Add mixin to replace replicated get_policy_target
Fix adds a mixin to replace the replicated get_policy_target function. Duplicated code is removed from many classes and mixin is inherited. project_id, user_id and domain_id are now default in the generated policy_target dict but are set to None if the data doesn't support it, this is to provide the most flexibility for operators writing policy.json as discussed in the bug report. policy_target_attrs attribute added by the mixin is overwrittable by sub-classes of the mixin to override the defaults for custom policy_target information. Change-Id: I26759f145b8756bd1eef585c8107160277061523 Closes-Bug: 1317238
This commit is contained in:
parent
4fa1bbb15e
commit
107cf8b328
@ -22,13 +22,14 @@ from horizon.utils import filters
|
||||
from openstack_dashboard import api
|
||||
from openstack_dashboard.dashboards.project.instances \
|
||||
import tables as project_tables
|
||||
from openstack_dashboard import policy
|
||||
|
||||
|
||||
class AdminEditInstance(project_tables.EditInstance):
|
||||
url = "horizon:admin:instances:update"
|
||||
|
||||
|
||||
class MigrateInstance(tables.BatchAction):
|
||||
class MigrateInstance(policy.PolicyTargetMixin, tables.BatchAction):
|
||||
name = "migrate"
|
||||
action_present = _("Migrate")
|
||||
action_past = _("Scheduled migration (pending confirmation) of")
|
||||
@ -37,12 +38,6 @@ class MigrateInstance(tables.BatchAction):
|
||||
classes = ("btn-migrate", "btn-danger")
|
||||
policy_rules = (("compute", "compute_extension:admin_actions:migrate"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, 'tenant_id', None)
|
||||
return {"project_id": project_id}
|
||||
|
||||
def allowed(self, request, instance):
|
||||
return ((instance.status in project_tables.ACTIVE_STATES
|
||||
or instance.status == 'SHUTOFF')
|
||||
@ -52,7 +47,8 @@ class MigrateInstance(tables.BatchAction):
|
||||
api.nova.server_migrate(request, obj_id)
|
||||
|
||||
|
||||
class LiveMigrateInstance(tables.LinkAction):
|
||||
class LiveMigrateInstance(policy.PolicyTargetMixin,
|
||||
tables.LinkAction):
|
||||
name = "live_migrate"
|
||||
verbose_name = _("Live Migrate Instance")
|
||||
url = "horizon:admin:instances:live_migrate"
|
||||
@ -60,12 +56,6 @@ class LiveMigrateInstance(tables.LinkAction):
|
||||
policy_rules = (
|
||||
("compute", "compute_extension:admin_actions:migrateLive"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, 'tenant_id', None)
|
||||
return {"project_id": project_id}
|
||||
|
||||
def allowed(self, request, instance):
|
||||
return ((instance.status in project_tables.ACTIVE_STATES)
|
||||
and not project_tables.is_deleting(instance))
|
||||
|
@ -24,12 +24,12 @@ from horizon import tables
|
||||
from openstack_dashboard import api
|
||||
from openstack_dashboard.dashboards.project.networks.ports import \
|
||||
tables as project_tables
|
||||
|
||||
from openstack_dashboard import policy
|
||||
|
||||
LOG = logging.getLogger(__name__)
|
||||
|
||||
|
||||
class DeletePort(tables.DeleteAction):
|
||||
class DeletePort(policy.PolicyTargetMixin, tables.DeleteAction):
|
||||
@staticmethod
|
||||
def action_present(count):
|
||||
return ungettext_lazy(
|
||||
@ -48,12 +48,6 @@ class DeletePort(tables.DeleteAction):
|
||||
|
||||
policy_rules = (("network", "delete_port"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, 'tenant_id', None)
|
||||
return {"project_id": project_id}
|
||||
|
||||
def delete(self, request, obj_id):
|
||||
try:
|
||||
api.neutron.port_delete(request, obj_id)
|
||||
@ -79,7 +73,7 @@ class CreatePort(tables.LinkAction):
|
||||
return reverse(self.url, args=(network_id,))
|
||||
|
||||
|
||||
class UpdatePort(tables.LinkAction):
|
||||
class UpdatePort(policy.PolicyTargetMixin, tables.LinkAction):
|
||||
name = "update"
|
||||
verbose_name = _("Edit Port")
|
||||
url = "horizon:admin:networks:editport"
|
||||
@ -87,12 +81,6 @@ class UpdatePort(tables.LinkAction):
|
||||
icon = "pencil"
|
||||
policy_rules = (("network", "update_port"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, 'tenant_id', None)
|
||||
return {"project_id": project_id}
|
||||
|
||||
def get_link_url(self, port):
|
||||
network_id = self.table.kwargs['network_id']
|
||||
return reverse(self.url, args=(network_id, port.id))
|
||||
|
@ -23,12 +23,13 @@ from horizon import tables
|
||||
from horizon.utils import memoized
|
||||
|
||||
from openstack_dashboard import api
|
||||
from openstack_dashboard import policy
|
||||
|
||||
|
||||
LOG = logging.getLogger(__name__)
|
||||
|
||||
|
||||
class DeleteSubnet(tables.DeleteAction):
|
||||
class DeleteSubnet(policy.PolicyTargetMixin, tables.DeleteAction):
|
||||
@staticmethod
|
||||
def action_present(count):
|
||||
return ungettext_lazy(
|
||||
@ -46,12 +47,7 @@ class DeleteSubnet(tables.DeleteAction):
|
||||
)
|
||||
|
||||
policy_rules = (("network", "delete_subnet"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, 'tenant_id', None)
|
||||
return {"network:project_id": project_id}
|
||||
policy_target_attrs = (("network:project_id", "tenant_id"),)
|
||||
|
||||
def delete(self, request, obj_id):
|
||||
try:
|
||||
@ -65,39 +61,32 @@ class DeleteSubnet(tables.DeleteAction):
|
||||
exceptions.handle(request, msg, redirect=redirect)
|
||||
|
||||
|
||||
class CreateSubnet(tables.LinkAction):
|
||||
class CreateSubnet(policy.PolicyTargetMixin, tables.LinkAction):
|
||||
name = "create"
|
||||
verbose_name = _("Create Subnet")
|
||||
url = "horizon:admin:networks:addsubnet"
|
||||
classes = ("ajax-modal",)
|
||||
icon = "plus"
|
||||
policy_rules = (("network", "create_subnet"),)
|
||||
policy_target_attrs = (("network:project_id", "tenant_id"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
network = self.table._get_network()
|
||||
if network:
|
||||
project_id = getattr(network, 'tenant_id', None)
|
||||
return {"network:project_id": project_id}
|
||||
return super(CreateSubnet, self)\
|
||||
.get_policy_target(request, self.table._get_network())
|
||||
|
||||
def get_link_url(self, datum=None):
|
||||
network_id = self.table.kwargs['network_id']
|
||||
return reverse(self.url, args=(network_id,))
|
||||
|
||||
|
||||
class UpdateSubnet(tables.LinkAction):
|
||||
class UpdateSubnet(policy.PolicyTargetMixin, tables.LinkAction):
|
||||
name = "update"
|
||||
verbose_name = _("Edit Subnet")
|
||||
url = "horizon:admin:networks:editsubnet"
|
||||
classes = ("ajax-modal",)
|
||||
icon = "pencil"
|
||||
policy_rules = (("network", "update_subnet"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, 'tenant_id', None)
|
||||
return {"network:project_id": project_id}
|
||||
policy_target_attrs = (("network:project_id", "tenant_id"),)
|
||||
|
||||
def get_link_url(self, subnet):
|
||||
network_id = self.table.kwargs['network_id']
|
||||
|
@ -25,12 +25,12 @@ from horizon import tables
|
||||
from openstack_dashboard import api
|
||||
from openstack_dashboard.dashboards.project.networks \
|
||||
import tables as project_tables
|
||||
|
||||
from openstack_dashboard import policy
|
||||
|
||||
LOG = logging.getLogger(__name__)
|
||||
|
||||
|
||||
class DeleteNetwork(tables.DeleteAction):
|
||||
class DeleteNetwork(policy.PolicyTargetMixin, tables.DeleteAction):
|
||||
@staticmethod
|
||||
def action_present(count):
|
||||
return ungettext_lazy(
|
||||
@ -49,12 +49,6 @@ class DeleteNetwork(tables.DeleteAction):
|
||||
|
||||
policy_rules = (("network", "delete_network"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, 'tenant_id', None)
|
||||
return {"project_id": project_id}
|
||||
|
||||
def delete(self, request, obj_id):
|
||||
try:
|
||||
api.neutron.network_delete(request, obj_id)
|
||||
@ -74,7 +68,7 @@ class CreateNetwork(tables.LinkAction):
|
||||
policy_rules = (("network", "create_network"),)
|
||||
|
||||
|
||||
class EditNetwork(tables.LinkAction):
|
||||
class EditNetwork(policy.PolicyTargetMixin, tables.LinkAction):
|
||||
name = "update"
|
||||
verbose_name = _("Edit Network")
|
||||
url = "horizon:admin:networks:update"
|
||||
@ -82,12 +76,6 @@ class EditNetwork(tables.LinkAction):
|
||||
icon = "pencil"
|
||||
policy_rules = (("network", "update_network"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, 'tenant_id', None)
|
||||
return {"project_id": project_id}
|
||||
|
||||
|
||||
# def _get_subnets(network):
|
||||
# cidrs = [subnet.get('cidr') for subnet in network.subnets]
|
||||
|
@ -23,12 +23,6 @@ class DeleteRouter(r_tables.DeleteRouter):
|
||||
redirect_url = "horizon:admin:routers:index"
|
||||
policy_rules = (("network", "delete_router"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, 'tenant_id', None)
|
||||
return {"project_id": project_id}
|
||||
|
||||
def delete(self, request, obj_id):
|
||||
search_opts = {'device_owner': 'network:router_interface',
|
||||
'device_id': obj_id}
|
||||
|
@ -18,6 +18,7 @@ from horizon import messages
|
||||
from horizon import tables
|
||||
|
||||
from openstack_dashboard import api
|
||||
from openstack_dashboard import policy
|
||||
|
||||
|
||||
ENABLE = 0
|
||||
@ -39,7 +40,7 @@ class CreateUserLink(tables.LinkAction):
|
||||
return api.keystone.keystone_can_edit_user()
|
||||
|
||||
|
||||
class EditUserLink(tables.LinkAction):
|
||||
class EditUserLink(policy.PolicyTargetMixin, tables.LinkAction):
|
||||
name = "edit"
|
||||
verbose_name = _("Edit")
|
||||
url = "horizon:identity:users:update"
|
||||
@ -47,15 +48,13 @@ class EditUserLink(tables.LinkAction):
|
||||
icon = "pencil"
|
||||
policy_rules = (("identity", "identity:update_user"),
|
||||
("identity", "identity:list_projects"),)
|
||||
|
||||
def get_policy_target(self, request, user):
|
||||
return {"user_id": user.id}
|
||||
policy_target_attrs = (("user_id", "id"),)
|
||||
|
||||
def allowed(self, request, user):
|
||||
return api.keystone.keystone_can_edit_user()
|
||||
|
||||
|
||||
class ToggleEnabled(tables.BatchAction):
|
||||
class ToggleEnabled(policy.PolicyTargetMixin, tables.BatchAction):
|
||||
name = "toggle"
|
||||
|
||||
@staticmethod
|
||||
@ -89,11 +88,7 @@ class ToggleEnabled(tables.BatchAction):
|
||||
)
|
||||
classes = ("btn-toggle",)
|
||||
policy_rules = (("identity", "identity:update_user"),)
|
||||
|
||||
def get_policy_target(self, request, user=None):
|
||||
if user:
|
||||
return {"user_id": user.id}
|
||||
return {}
|
||||
policy_target_attrs = (("user_id", "id"),)
|
||||
|
||||
def allowed(self, request, user=None):
|
||||
if not api.keystone.keystone_can_edit_user():
|
||||
|
@ -20,6 +20,7 @@ from django.utils.translation import ungettext_lazy
|
||||
from horizon import tables
|
||||
|
||||
from openstack_dashboard import api
|
||||
from openstack_dashboard import policy
|
||||
from openstack_dashboard.utils import filters
|
||||
|
||||
|
||||
@ -27,7 +28,7 @@ POLICY_CHECK = getattr(settings, "POLICY_CHECK_FUNCTION",
|
||||
lambda policy, request, target: True)
|
||||
|
||||
|
||||
class DeleteGroup(tables.DeleteAction):
|
||||
class DeleteGroup(policy.PolicyTargetMixin, tables.DeleteAction):
|
||||
|
||||
@staticmethod
|
||||
def action_present(count):
|
||||
@ -45,12 +46,6 @@ class DeleteGroup(tables.DeleteAction):
|
||||
count
|
||||
)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, 'tenant_id', None)
|
||||
return {"project_id": project_id}
|
||||
|
||||
def allowed(self, request, security_group=None):
|
||||
policy_target = self.get_policy_target(request, security_group)
|
||||
if api.base.is_service_enabled(request, "network"):
|
||||
@ -85,19 +80,13 @@ class CreateGroup(tables.LinkAction):
|
||||
return POLICY_CHECK(policy, request, target={})
|
||||
|
||||
|
||||
class EditGroup(tables.LinkAction):
|
||||
class EditGroup(policy.PolicyTargetMixin, tables.LinkAction):
|
||||
name = "edit"
|
||||
verbose_name = _("Edit Security Group")
|
||||
url = "horizon:project:access_and_security:security_groups:update"
|
||||
classes = ("ajax-modal",)
|
||||
icon = "pencil"
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, 'tenant_id', None)
|
||||
return {"project_id": project_id}
|
||||
|
||||
def allowed(self, request, security_group=None):
|
||||
policy_target = self.get_policy_target(request, security_group)
|
||||
if api.base.is_service_enabled(request, "network"):
|
||||
@ -113,18 +102,12 @@ class EditGroup(tables.LinkAction):
|
||||
return security_group.name != 'default'
|
||||
|
||||
|
||||
class ManageRules(tables.LinkAction):
|
||||
class ManageRules(policy.PolicyTargetMixin, tables.LinkAction):
|
||||
name = "manage_rules"
|
||||
verbose_name = _("Manage Rules")
|
||||
url = "horizon:project:access_and_security:security_groups:detail"
|
||||
icon = "pencil"
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, 'tenant_id', None)
|
||||
return {"project_id": project_id}
|
||||
|
||||
def allowed(self, request, security_group=None):
|
||||
policy_target = self.get_policy_target(request, security_group)
|
||||
if api.base.is_service_enabled(request, "network"):
|
||||
|
@ -19,6 +19,7 @@ from django.template import defaultfilters as filters
|
||||
from django.utils.translation import ugettext_lazy as _
|
||||
|
||||
from horizon import tables
|
||||
from openstack_dashboard import policy
|
||||
|
||||
|
||||
class AddRuleLink(tables.LinkAction):
|
||||
@ -47,7 +48,7 @@ class AddFirewallLink(tables.LinkAction):
|
||||
policy_rules = (("network", "create_firewall"),)
|
||||
|
||||
|
||||
class DeleteRuleLink(tables.DeleteAction):
|
||||
class DeleteRuleLink(policy.PolicyTargetMixin, tables.DeleteAction):
|
||||
name = "deleterule"
|
||||
action_present = _("Delete")
|
||||
action_past = _("Scheduled deletion of %(data_type)s")
|
||||
@ -55,14 +56,8 @@ class DeleteRuleLink(tables.DeleteAction):
|
||||
data_type_plural = _("Rules")
|
||||
policy_rules = (("network", "delete_firewall_rule"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, 'tenant_id', None)
|
||||
return {"project_id": project_id}
|
||||
|
||||
|
||||
class DeletePolicyLink(tables.DeleteAction):
|
||||
class DeletePolicyLink(policy.PolicyTargetMixin, tables.DeleteAction):
|
||||
name = "deletepolicy"
|
||||
action_present = _("Delete")
|
||||
action_past = _("Scheduled deletion of %(data_type)s")
|
||||
@ -70,14 +65,9 @@ class DeletePolicyLink(tables.DeleteAction):
|
||||
data_type_plural = _("Policies")
|
||||
policy_rules = (("network", "delete_firewall_policy"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, 'tenant_id', None)
|
||||
return {"project_id": project_id}
|
||||
|
||||
|
||||
class DeleteFirewallLink(tables.DeleteAction):
|
||||
class DeleteFirewallLink(policy.PolicyTargetMixin,
|
||||
tables.DeleteAction):
|
||||
name = "deletefirewall"
|
||||
action_present = _("Delete")
|
||||
action_past = _("Scheduled deletion of %(data_type)s")
|
||||
@ -85,99 +75,65 @@ class DeleteFirewallLink(tables.DeleteAction):
|
||||
data_type_plural = _("Firewalls")
|
||||
policy_rules = (("network", "delete_firewall"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, 'tenant_id', None)
|
||||
return {"project_id": project_id}
|
||||
|
||||
|
||||
class UpdateRuleLink(tables.LinkAction):
|
||||
class UpdateRuleLink(policy.PolicyTargetMixin, tables.LinkAction):
|
||||
name = "updaterule"
|
||||
verbose_name = _("Edit Rule")
|
||||
classes = ("ajax-modal", "btn-update",)
|
||||
policy_rules = (("network", "update_firewall_rule"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, 'tenant_id', None)
|
||||
return {"project_id": project_id}
|
||||
|
||||
def get_link_url(self, rule):
|
||||
base_url = reverse("horizon:project:firewalls:updaterule",
|
||||
kwargs={'rule_id': rule.id})
|
||||
return base_url
|
||||
|
||||
|
||||
class UpdatePolicyLink(tables.LinkAction):
|
||||
class UpdatePolicyLink(policy.PolicyTargetMixin, tables.LinkAction):
|
||||
name = "updatepolicy"
|
||||
verbose_name = _("Edit Policy")
|
||||
classes = ("ajax-modal", "btn-update",)
|
||||
policy_rules = (("network", "update_firewall_policy"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, 'tenant_id', None)
|
||||
return {"project_id": project_id}
|
||||
|
||||
def get_link_url(self, policy):
|
||||
base_url = reverse("horizon:project:firewalls:updatepolicy",
|
||||
kwargs={'policy_id': policy.id})
|
||||
return base_url
|
||||
|
||||
|
||||
class UpdateFirewallLink(tables.LinkAction):
|
||||
class UpdateFirewallLink(policy.PolicyTargetMixin, tables.LinkAction):
|
||||
name = "updatefirewall"
|
||||
verbose_name = _("Edit Firewall")
|
||||
classes = ("ajax-modal", "btn-update",)
|
||||
policy_rules = (("network", "update_firewall"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, 'tenant_id', None)
|
||||
return {"project_id": project_id}
|
||||
|
||||
def get_link_url(self, firewall):
|
||||
base_url = reverse("horizon:project:firewalls:updatefirewall",
|
||||
kwargs={'firewall_id': firewall.id})
|
||||
return base_url
|
||||
|
||||
|
||||
class InsertRuleToPolicyLink(tables.LinkAction):
|
||||
class InsertRuleToPolicyLink(policy.PolicyTargetMixin,
|
||||
tables.LinkAction):
|
||||
name = "insertrule"
|
||||
verbose_name = _("Insert Rule")
|
||||
classes = ("ajax-modal", "btn-update",)
|
||||
policy_rules = (("network", "get_firewall_policy"),
|
||||
("network", "insert_rule"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, 'tenant_id', None)
|
||||
return {"project_id": project_id}
|
||||
|
||||
def get_link_url(self, policy):
|
||||
base_url = reverse("horizon:project:firewalls:insertrule",
|
||||
kwargs={'policy_id': policy.id})
|
||||
return base_url
|
||||
|
||||
|
||||
class RemoveRuleFromPolicyLink(tables.LinkAction):
|
||||
class RemoveRuleFromPolicyLink(policy.PolicyTargetMixin,
|
||||
tables.LinkAction):
|
||||
name = "removerule"
|
||||
verbose_name = _("Remove Rule")
|
||||
classes = ("ajax-modal", "btn-danger",)
|
||||
policy_rules = (("network", "get_firewall_policy"),
|
||||
("network", "remove_rule"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, 'tenant_id', None)
|
||||
return {"project_id": project_id}
|
||||
|
||||
def get_link_url(self, policy):
|
||||
base_url = reverse("horizon:project:firewalls:removerule",
|
||||
kwargs={'policy_id': policy.id})
|
||||
|
@ -43,6 +43,7 @@ from openstack_dashboard.dashboards.project.instances.workflows \
|
||||
import resize_instance
|
||||
from openstack_dashboard.dashboards.project.instances.workflows \
|
||||
import update_instance
|
||||
from openstack_dashboard import policy
|
||||
|
||||
|
||||
LOG = logging.getLogger(__name__)
|
||||
@ -77,7 +78,7 @@ def is_deleting(instance):
|
||||
return task_state.lower() == "deleting"
|
||||
|
||||
|
||||
class TerminateInstance(tables.BatchAction):
|
||||
class TerminateInstance(policy.PolicyTargetMixin, tables.BatchAction):
|
||||
name = "terminate"
|
||||
classes = ("btn-danger",)
|
||||
icon = "off"
|
||||
@ -99,12 +100,6 @@ class TerminateInstance(tables.BatchAction):
|
||||
count
|
||||
)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, 'tenant_id', None)
|
||||
return {"project_id": project_id}
|
||||
|
||||
def allowed(self, request, instance=None):
|
||||
"""Allow terminate action if instance not currently being deleted."""
|
||||
return not is_deleting(instance)
|
||||
@ -113,7 +108,7 @@ class TerminateInstance(tables.BatchAction):
|
||||
api.nova.server_delete(request, obj_id)
|
||||
|
||||
|
||||
class RebootInstance(tables.BatchAction):
|
||||
class RebootInstance(policy.PolicyTargetMixin, tables.BatchAction):
|
||||
name = "reboot"
|
||||
classes = ('btn-danger', 'btn-reboot')
|
||||
policy_rules = (("compute", "compute:reboot"),)
|
||||
@ -134,12 +129,6 @@ class RebootInstance(tables.BatchAction):
|
||||
count
|
||||
)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, 'tenant_id', None)
|
||||
return {"project_id": project_id}
|
||||
|
||||
def allowed(self, request, instance=None):
|
||||
if instance is not None:
|
||||
return ((instance.status in ACTIVE_STATES
|
||||
@ -353,7 +342,7 @@ class LaunchLink(tables.LinkAction):
|
||||
return HttpResponse(self.render())
|
||||
|
||||
|
||||
class EditInstance(tables.LinkAction):
|
||||
class EditInstance(policy.PolicyTargetMixin, tables.LinkAction):
|
||||
name = "edit"
|
||||
verbose_name = _("Edit Instance")
|
||||
url = "horizon:project:instances:update"
|
||||
@ -361,12 +350,6 @@ class EditInstance(tables.LinkAction):
|
||||
icon = "pencil"
|
||||
policy_rules = (("compute", "compute:update"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, 'tenant_id', None)
|
||||
return {"project_id": project_id}
|
||||
|
||||
def get_link_url(self, project):
|
||||
return self._get_link_url(project, 'instance_info')
|
||||
|
||||
@ -395,7 +378,7 @@ class EditInstanceSecurityGroups(EditInstance):
|
||||
request.user.tenant_id == instance.tenant_id)
|
||||
|
||||
|
||||
class CreateSnapshot(tables.LinkAction):
|
||||
class CreateSnapshot(policy.PolicyTargetMixin, tables.LinkAction):
|
||||
name = "snapshot"
|
||||
verbose_name = _("Create Snapshot")
|
||||
url = "horizon:project:images:snapshots:create"
|
||||
@ -403,30 +386,18 @@ class CreateSnapshot(tables.LinkAction):
|
||||
icon = "camera"
|
||||
policy_rules = (("compute", "compute:snapshot"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, 'tenant_id', None)
|
||||
return {"project_id": project_id}
|
||||
|
||||
def allowed(self, request, instance=None):
|
||||
return instance.status in SNAPSHOT_READY_STATES \
|
||||
and not is_deleting(instance)
|
||||
|
||||
|
||||
class ConsoleLink(tables.LinkAction):
|
||||
class ConsoleLink(policy.PolicyTargetMixin, tables.LinkAction):
|
||||
name = "console"
|
||||
verbose_name = _("Console")
|
||||
url = "horizon:project:instances:detail"
|
||||
classes = ("btn-console",)
|
||||
policy_rules = (("compute", "compute_extension:consoles"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, 'tenant_id', None)
|
||||
return {"project_id": project_id}
|
||||
|
||||
def allowed(self, request, instance=None):
|
||||
# We check if ConsoleLink is allowed only if settings.CONSOLE_TYPE is
|
||||
# not set at all, or if it's set to any value other than None or False.
|
||||
@ -440,19 +411,13 @@ class ConsoleLink(tables.LinkAction):
|
||||
return "?".join([base_url, tab_query_string])
|
||||
|
||||
|
||||
class LogLink(tables.LinkAction):
|
||||
class LogLink(policy.PolicyTargetMixin, tables.LinkAction):
|
||||
name = "log"
|
||||
verbose_name = _("View Log")
|
||||
url = "horizon:project:instances:detail"
|
||||
classes = ("btn-log",)
|
||||
policy_rules = (("compute", "compute_extension:console_output"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, 'tenant_id', None)
|
||||
return {"project_id": project_id}
|
||||
|
||||
def allowed(self, request, instance=None):
|
||||
return instance.status in ACTIVE_STATES and not is_deleting(instance)
|
||||
|
||||
@ -463,19 +428,13 @@ class LogLink(tables.LinkAction):
|
||||
return "?".join([base_url, tab_query_string])
|
||||
|
||||
|
||||
class ResizeLink(tables.LinkAction):
|
||||
class ResizeLink(policy.PolicyTargetMixin, tables.LinkAction):
|
||||
name = "resize"
|
||||
verbose_name = _("Resize Instance")
|
||||
url = "horizon:project:instances:resize"
|
||||
classes = ("ajax-modal", "btn-resize")
|
||||
policy_rules = (("compute", "compute:resize"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, 'tenant_id', None)
|
||||
return {"project_id": project_id}
|
||||
|
||||
def get_link_url(self, project):
|
||||
return self._get_link_url(project, 'flavor_choice')
|
||||
|
||||
@ -493,18 +452,12 @@ class ResizeLink(tables.LinkAction):
|
||||
and not is_deleting(instance))
|
||||
|
||||
|
||||
class ConfirmResize(tables.Action):
|
||||
class ConfirmResize(policy.PolicyTargetMixin, tables.Action):
|
||||
name = "confirm"
|
||||
verbose_name = _("Confirm Resize/Migrate")
|
||||
classes = ("btn-confirm", "btn-action-required")
|
||||
policy_rules = (("compute", "compute:confirm_resize"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, 'tenant_id', None)
|
||||
return {"project_id": project_id}
|
||||
|
||||
def allowed(self, request, instance):
|
||||
return instance.status == 'VERIFY_RESIZE'
|
||||
|
||||
@ -512,18 +465,12 @@ class ConfirmResize(tables.Action):
|
||||
api.nova.server_confirm_resize(request, instance)
|
||||
|
||||
|
||||
class RevertResize(tables.Action):
|
||||
class RevertResize(policy.PolicyTargetMixin, tables.Action):
|
||||
name = "revert"
|
||||
verbose_name = _("Revert Resize/Migrate")
|
||||
classes = ("btn-revert", "btn-action-required")
|
||||
policy_rules = (("compute", "compute:revert_resize"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, 'tenant_id', None)
|
||||
return {"project_id": project_id}
|
||||
|
||||
def allowed(self, request, instance):
|
||||
return instance.status == 'VERIFY_RESIZE'
|
||||
|
||||
@ -531,19 +478,13 @@ class RevertResize(tables.Action):
|
||||
api.nova.server_revert_resize(request, instance)
|
||||
|
||||
|
||||
class RebuildInstance(tables.LinkAction):
|
||||
class RebuildInstance(policy.PolicyTargetMixin, tables.LinkAction):
|
||||
name = "rebuild"
|
||||
verbose_name = _("Rebuild Instance")
|
||||
classes = ("btn-rebuild", "ajax-modal")
|
||||
url = "horizon:project:instances:rebuild"
|
||||
policy_rules = (("compute", "compute:rebuild"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, 'tenant_id', None)
|
||||
return {"project_id": project_id}
|
||||
|
||||
def allowed(self, request, instance):
|
||||
return ((instance.status in ACTIVE_STATES
|
||||
or instance.status == 'SHUTOFF')
|
||||
@ -577,7 +518,7 @@ class DecryptInstancePassword(tables.LinkAction):
|
||||
keypair_name])
|
||||
|
||||
|
||||
class AssociateIP(tables.LinkAction):
|
||||
class AssociateIP(policy.PolicyTargetMixin, tables.LinkAction):
|
||||
name = "associate"
|
||||
verbose_name = _("Associate Floating IP")
|
||||
url = "horizon:project:access_and_security:floating_ips:associate"
|
||||
@ -585,12 +526,6 @@ class AssociateIP(tables.LinkAction):
|
||||
icon = "link"
|
||||
policy_rules = (("compute", "network:associate_floating_ip"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, 'tenant_id', None)
|
||||
return {"project_id": project_id}
|
||||
|
||||
def allowed(self, request, instance):
|
||||
if not api.network.floating_ip_supported(request):
|
||||
return False
|
||||
@ -607,18 +542,12 @@ class AssociateIP(tables.LinkAction):
|
||||
return "?".join([base_url, params])
|
||||
|
||||
|
||||
class SimpleAssociateIP(tables.Action):
|
||||
class SimpleAssociateIP(policy.PolicyTargetMixin, tables.Action):
|
||||
name = "associate-simple"
|
||||
verbose_name = _("Associate Floating IP")
|
||||
icon = "link"
|
||||
policy_rules = (("compute", "network:associate_floating_ip"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, 'tenant_id', None)
|
||||
return {"project_id": project_id}
|
||||
|
||||
def allowed(self, request, instance):
|
||||
if not api.network.floating_ip_simple_associate_supported(request):
|
||||
return False
|
||||
@ -642,18 +571,12 @@ class SimpleAssociateIP(tables.Action):
|
||||
return shortcuts.redirect("horizon:project:instances:index")
|
||||
|
||||
|
||||
class SimpleDisassociateIP(tables.Action):
|
||||
class SimpleDisassociateIP(policy.PolicyTargetMixin, tables.Action):
|
||||
name = "disassociate"
|
||||
verbose_name = _("Disassociate Floating IP")
|
||||
classes = ("btn-danger", "btn-disassociate",)
|
||||
policy_rules = (("compute", "network:disassociate_floating_ip"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, 'tenant_id', None)
|
||||
return {"project_id": project_id}
|
||||
|
||||
def allowed(self, request, instance):
|
||||
if not api.network.floating_ip_supported(request):
|
||||
return False
|
||||
@ -725,7 +648,7 @@ class UpdateRow(tables.Row):
|
||||
return instance
|
||||
|
||||
|
||||
class StartInstance(tables.BatchAction):
|
||||
class StartInstance(policy.PolicyTargetMixin, tables.BatchAction):
|
||||
name = "start"
|
||||
policy_rules = (("compute", "compute:start"),)
|
||||
|
||||
@ -745,12 +668,6 @@ class StartInstance(tables.BatchAction):
|
||||
count
|
||||
)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, 'tenant_id', None)
|
||||
return {"project_id": project_id}
|
||||
|
||||
def allowed(self, request, instance):
|
||||
return instance.status in ("SHUTDOWN", "SHUTOFF", "CRASHED")
|
||||
|
||||
@ -758,7 +675,7 @@ class StartInstance(tables.BatchAction):
|
||||
api.nova.server_start(request, obj_id)
|
||||
|
||||
|
||||
class StopInstance(tables.BatchAction):
|
||||
class StopInstance(policy.PolicyTargetMixin, tables.BatchAction):
|
||||
name = "stop"
|
||||
classes = ('btn-danger',)
|
||||
policy_rules = (("compute", "compute:stop"),)
|
||||
@ -781,12 +698,6 @@ class StopInstance(tables.BatchAction):
|
||||
count
|
||||
)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, 'tenant_id', None)
|
||||
return {"project_id": project_id}
|
||||
|
||||
def allowed(self, request, instance):
|
||||
return ((get_power_state(instance)
|
||||
in ("RUNNING", "PAUSED", "SUSPENDED"))
|
||||
|
@ -22,6 +22,7 @@ from horizon import exceptions
|
||||
from horizon import tables
|
||||
|
||||
from openstack_dashboard import api
|
||||
from openstack_dashboard import policy
|
||||
|
||||
|
||||
class AddPoolLink(tables.LinkAction):
|
||||
@ -69,7 +70,7 @@ class AddMonitorLink(tables.LinkAction):
|
||||
policy_rules = (("network", "create_health_monitor"),)
|
||||
|
||||
|
||||
class DeleteVipLink(tables.DeleteAction):
|
||||
class DeleteVipLink(policy.PolicyTargetMixin, tables.DeleteAction):
|
||||
name = "deletevip"
|
||||
action_present = _("Delete")
|
||||
action_past = _("Scheduled deletion of %(data_type)s")
|
||||
@ -77,19 +78,13 @@ class DeleteVipLink(tables.DeleteAction):
|
||||
data_type_plural = _("VIPs")
|
||||
policy_rules = (("network", "delete_vip"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, 'tenant_id', None)
|
||||
return {"project_id": project_id}
|
||||
|
||||
def allowed(self, request, datum=None):
|
||||
if datum and not datum.vip_id:
|
||||
return False
|
||||
return True
|
||||
|
||||
|
||||
class DeletePoolLink(tables.DeleteAction):
|
||||
class DeletePoolLink(policy.PolicyTargetMixin, tables.DeleteAction):
|
||||
name = "deletepool"
|
||||
action_present = _("Delete")
|
||||
action_past = _("Scheduled deletion of %(data_type)s")
|
||||
@ -97,19 +92,14 @@ class DeletePoolLink(tables.DeleteAction):
|
||||
data_type_plural = _("Pools")
|
||||
policy_rules = (("network", "delete_pool"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, 'tenant_id', None)
|
||||
return {"project_id": project_id}
|
||||
|
||||
def allowed(self, request, datum=None):
|
||||
if datum and datum.vip_id:
|
||||
return False
|
||||
return True
|
||||
|
||||
|
||||
class DeleteMonitorLink(tables.DeleteAction):
|
||||
class DeleteMonitorLink(policy.PolicyTargetMixin,
|
||||
tables.DeleteAction):
|
||||
name = "deletemonitor"
|
||||
action_present = _("Delete")
|
||||
action_past = _("Scheduled deletion of %(data_type)s")
|
||||
@ -117,14 +107,8 @@ class DeleteMonitorLink(tables.DeleteAction):
|
||||
data_type_plural = _("Monitors")
|
||||
policy_rules = (("network", "delete_health_monitor"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, 'tenant_id', None)
|
||||
return {"project_id": project_id}
|
||||
|
||||
|
||||
class DeleteMemberLink(tables.DeleteAction):
|
||||
class DeleteMemberLink(policy.PolicyTargetMixin, tables.DeleteAction):
|
||||
name = "deletemember"
|
||||
action_present = _("Delete")
|
||||
action_past = _("Scheduled deletion of %(data_type)s")
|
||||
@ -132,43 +116,25 @@ class DeleteMemberLink(tables.DeleteAction):
|
||||
data_type_plural = _("Members")
|
||||
policy_rules = (("network", "delete_member"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, 'tenant_id', None)
|
||||
return {"project_id": project_id}
|
||||
|
||||
|
||||
class UpdatePoolLink(tables.LinkAction):
|
||||
class UpdatePoolLink(policy.PolicyTargetMixin, tables.LinkAction):
|
||||
name = "updatepool"
|
||||
verbose_name = _("Edit Pool")
|
||||
classes = ("ajax-modal", "btn-update",)
|
||||
policy_rules = (("network", "update_pool"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, 'tenant_id', None)
|
||||
return {"project_id": project_id}
|
||||
|
||||
def get_link_url(self, pool):
|
||||
base_url = reverse("horizon:project:loadbalancers:updatepool",
|
||||
kwargs={'pool_id': pool.id})
|
||||
return base_url
|
||||
|
||||
|
||||
class UpdateVipLink(tables.LinkAction):
|
||||
class UpdateVipLink(policy.PolicyTargetMixin, tables.LinkAction):
|
||||
name = "updatevip"
|
||||
verbose_name = _("Edit VIP")
|
||||
classes = ("ajax-modal", "btn-update",)
|
||||
policy_rules = (("network", "update_vip"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, 'tenant_id', None)
|
||||
return {"project_id": project_id}
|
||||
|
||||
def get_link_url(self, pool):
|
||||
base_url = reverse("horizon:project:loadbalancers:updatevip",
|
||||
kwargs={'vip_id': pool.vip_id})
|
||||
@ -180,36 +146,24 @@ class UpdateVipLink(tables.LinkAction):
|
||||
return True
|
||||
|
||||
|
||||
class UpdateMemberLink(tables.LinkAction):
|
||||
class UpdateMemberLink(policy.PolicyTargetMixin, tables.LinkAction):
|
||||
name = "updatemember"
|
||||
verbose_name = _("Edit Member")
|
||||
classes = ("ajax-modal", "btn-update",)
|
||||
policy_rules = (("network", "update_member"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, 'tenant_id', None)
|
||||
return {"project_id": project_id}
|
||||
|
||||
def get_link_url(self, member):
|
||||
base_url = reverse("horizon:project:loadbalancers:updatemember",
|
||||
kwargs={'member_id': member.id})
|
||||
return base_url
|
||||
|
||||
|
||||
class UpdateMonitorLink(tables.LinkAction):
|
||||
class UpdateMonitorLink(policy.PolicyTargetMixin, tables.LinkAction):
|
||||
name = "updatemonitor"
|
||||
verbose_name = _("Edit Monitor")
|
||||
classes = ("ajax-modal", "btn-update",)
|
||||
policy_rules = (("network", "update_health_monitor"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, 'tenant_id', None)
|
||||
return {"project_id": project_id}
|
||||
|
||||
def get_link_url(self, monitor):
|
||||
base_url = reverse("horizon:project:loadbalancers:updatemonitor",
|
||||
kwargs={'monitor_id': monitor.id})
|
||||
@ -224,7 +178,8 @@ def get_vip_link(pool):
|
||||
return None
|
||||
|
||||
|
||||
class AddPMAssociationLink(tables.LinkAction):
|
||||
class AddPMAssociationLink(policy.PolicyTargetMixin,
|
||||
tables.LinkAction):
|
||||
name = "addassociation"
|
||||
verbose_name = _("Associate Monitor")
|
||||
url = "horizon:project:loadbalancers:addassociation"
|
||||
@ -232,12 +187,6 @@ class AddPMAssociationLink(tables.LinkAction):
|
||||
icon = "plus"
|
||||
policy_rules = (("network", "create_pool_health_monitor"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, 'tenant_id', None)
|
||||
return {"project_id": project_id}
|
||||
|
||||
def allowed(self, request, datum=None):
|
||||
try:
|
||||
tenant_id = request.user.tenant_id
|
||||
@ -252,7 +201,8 @@ class AddPMAssociationLink(tables.LinkAction):
|
||||
return False
|
||||
|
||||
|
||||
class DeletePMAssociationLink(tables.LinkAction):
|
||||
class DeletePMAssociationLink(policy.PolicyTargetMixin,
|
||||
tables.LinkAction):
|
||||
name = "deleteassociation"
|
||||
verbose_name = _("Disassociate Monitor")
|
||||
url = "horizon:project:loadbalancers:deleteassociation"
|
||||
@ -260,12 +210,6 @@ class DeletePMAssociationLink(tables.LinkAction):
|
||||
icon = "remove"
|
||||
policy_rules = (("network", "delete_pool_health_monitor"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, 'tenant_id', None)
|
||||
return {"project_id": project_id}
|
||||
|
||||
def allowed(self, request, datum=None):
|
||||
if datum and not datum['health_monitors']:
|
||||
return False
|
||||
|
@ -19,6 +19,7 @@ from django.utils.translation import ugettext_lazy as _
|
||||
from horizon import tables
|
||||
|
||||
from openstack_dashboard import api
|
||||
from openstack_dashboard import policy
|
||||
|
||||
|
||||
def get_fixed_ips(port):
|
||||
@ -36,7 +37,7 @@ def get_attached(port):
|
||||
return _('Detached')
|
||||
|
||||
|
||||
class UpdatePort(tables.LinkAction):
|
||||
class UpdatePort(policy.PolicyTargetMixin, tables.LinkAction):
|
||||
name = "update"
|
||||
verbose_name = _("Edit Port")
|
||||
url = "horizon:project:networks:editport"
|
||||
@ -44,12 +45,6 @@ class UpdatePort(tables.LinkAction):
|
||||
icon = "pencil"
|
||||
policy_rules = (("network", "update_port"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, 'tenant_id', None)
|
||||
return {"project_id": project_id}
|
||||
|
||||
def get_link_url(self, port):
|
||||
network_id = self.table.kwargs['network_id']
|
||||
return reverse(self.url, args=(network_id, port.id))
|
||||
|
@ -23,6 +23,7 @@ from horizon import tables
|
||||
from horizon.utils import memoized
|
||||
|
||||
from openstack_dashboard import api
|
||||
from openstack_dashboard import policy
|
||||
|
||||
|
||||
LOG = logging.getLogger(__name__)
|
||||
@ -40,16 +41,12 @@ class CheckNetworkEditable(object):
|
||||
return True
|
||||
|
||||
|
||||
class DeleteSubnet(CheckNetworkEditable, tables.DeleteAction):
|
||||
class DeleteSubnet(policy.PolicyTargetMixin, CheckNetworkEditable,
|
||||
tables.DeleteAction):
|
||||
data_type_singular = _("Subnet")
|
||||
data_type_plural = _("Subnets")
|
||||
policy_rules = (("network", "delete_subnet"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, 'tenant_id', None)
|
||||
return {"network:project_id": project_id}
|
||||
policy_target_attrs = (("network:project_id", "tenant_id"),)
|
||||
|
||||
def delete(self, request, obj_id):
|
||||
try:
|
||||
@ -63,39 +60,34 @@ class DeleteSubnet(CheckNetworkEditable, tables.DeleteAction):
|
||||
exceptions.handle(request, msg, redirect=redirect)
|
||||
|
||||
|
||||
class CreateSubnet(CheckNetworkEditable, tables.LinkAction):
|
||||
class CreateSubnet(policy.PolicyTargetMixin, CheckNetworkEditable,
|
||||
tables.LinkAction):
|
||||
name = "create"
|
||||
verbose_name = _("Create Subnet")
|
||||
url = "horizon:project:networks:addsubnet"
|
||||
classes = ("ajax-modal",)
|
||||
icon = "plus"
|
||||
policy_rules = (("network", "create_subnet"),)
|
||||
policy_target_attrs = (("network:project_id", "tenant_id"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
network = self.table._get_network()
|
||||
if network:
|
||||
project_id = getattr(network, 'tenant_id', None)
|
||||
return {"network:project_id": project_id}
|
||||
return super(CreateSubnet, self)\
|
||||
.get_policy_target(request, self.table._get_network())
|
||||
|
||||
def get_link_url(self, datum=None):
|
||||
network_id = self.table.kwargs['network_id']
|
||||
return reverse(self.url, args=(network_id,))
|
||||
|
||||
|
||||
class UpdateSubnet(CheckNetworkEditable, tables.LinkAction):
|
||||
class UpdateSubnet(policy.PolicyTargetMixin, CheckNetworkEditable,
|
||||
tables.LinkAction):
|
||||
name = "update"
|
||||
verbose_name = _("Edit Subnet")
|
||||
url = "horizon:project:networks:editsubnet"
|
||||
classes = ("ajax-modal",)
|
||||
icon = "pencil"
|
||||
policy_rules = (("network", "update_subnet"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, 'tenant_id', None)
|
||||
return {"network:project_id": project_id}
|
||||
policy_target_attrs = (("network:project_id", "tenant_id"),)
|
||||
|
||||
def get_link_url(self, subnet):
|
||||
network_id = self.table.kwargs['network_id']
|
||||
|
@ -22,7 +22,7 @@ from horizon import exceptions
|
||||
from horizon import tables
|
||||
|
||||
from openstack_dashboard import api
|
||||
|
||||
from openstack_dashboard import policy
|
||||
|
||||
LOG = logging.getLogger(__name__)
|
||||
|
||||
@ -37,17 +37,12 @@ class CheckNetworkEditable(object):
|
||||
return True
|
||||
|
||||
|
||||
class DeleteNetwork(CheckNetworkEditable, tables.DeleteAction):
|
||||
class DeleteNetwork(policy.PolicyTargetMixin, CheckNetworkEditable,
|
||||
tables.DeleteAction):
|
||||
data_type_singular = _("Network")
|
||||
data_type_plural = _("Networks")
|
||||
policy_rules = (("network", "delete_network"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, 'tenant_id', None)
|
||||
return {"project_id": project_id}
|
||||
|
||||
def delete(self, request, network_id):
|
||||
try:
|
||||
# Retrieve existing subnets belonging to the network.
|
||||
@ -76,7 +71,8 @@ class CreateNetwork(tables.LinkAction):
|
||||
policy_rules = (("network", "create_network"),)
|
||||
|
||||
|
||||
class EditNetwork(CheckNetworkEditable, tables.LinkAction):
|
||||
class EditNetwork(policy.PolicyTargetMixin, CheckNetworkEditable,
|
||||
tables.LinkAction):
|
||||
name = "update"
|
||||
verbose_name = _("Edit Network")
|
||||
url = "horizon:project:networks:update"
|
||||
@ -84,26 +80,16 @@ class EditNetwork(CheckNetworkEditable, tables.LinkAction):
|
||||
icon = "pencil"
|
||||
policy_rules = (("network", "update_network"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, 'tenant_id', None)
|
||||
return {"project_id": project_id}
|
||||
|
||||
|
||||
class CreateSubnet(CheckNetworkEditable, tables.LinkAction):
|
||||
class CreateSubnet(policy.PolicyTargetMixin, CheckNetworkEditable,
|
||||
tables.LinkAction):
|
||||
name = "subnet"
|
||||
verbose_name = _("Add Subnet")
|
||||
url = "horizon:project:networks:addsubnet"
|
||||
classes = ("ajax-modal",)
|
||||
icon = "plus"
|
||||
policy_rules = (("network", "create_subnet"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, 'tenant_id', None)
|
||||
return {"network:project_id": project_id}
|
||||
policy_target_attrs = (("network:project_id", "tenant_id"),)
|
||||
|
||||
|
||||
def get_subnets(network):
|
||||
|
@ -19,13 +19,14 @@ from django.utils.translation import ugettext_lazy as _
|
||||
|
||||
from openstack_dashboard.dashboards.project.routers.extensions.routerrules\
|
||||
import rulemanager
|
||||
from openstack_dashboard import policy
|
||||
|
||||
from horizon import tables
|
||||
|
||||
LOG = logging.getLogger(__name__)
|
||||
|
||||
|
||||
class AddRouterRule(tables.LinkAction):
|
||||
class AddRouterRule(policy.PolicyTargetMixin, tables.LinkAction):
|
||||
name = "create"
|
||||
verbose_name = _("Add Router Rule")
|
||||
url = "horizon:project:routers:addrouterrule"
|
||||
@ -33,29 +34,17 @@ class AddRouterRule(tables.LinkAction):
|
||||
icon = "plus"
|
||||
policy_rules = (("network", "update_router"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, 'tenant_id', None)
|
||||
return {"project_id": project_id}
|
||||
|
||||
def get_link_url(self, datum=None):
|
||||
router_id = self.table.kwargs['router_id']
|
||||
return reverse(self.url, args=(router_id,))
|
||||
|
||||
|
||||
class RemoveRouterRule(tables.DeleteAction):
|
||||
class RemoveRouterRule(policy.PolicyTargetMixin, tables.DeleteAction):
|
||||
data_type_singular = _("Router Rule")
|
||||
data_type_plural = _("Router Rules")
|
||||
failure_url = 'horizon:project:routers:detail'
|
||||
policy_rules = (("network", "update_router"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, 'tenant_id', None)
|
||||
return {"project_id": project_id}
|
||||
|
||||
def delete(self, request, obj_id):
|
||||
router_id = self.table.kwargs['router_id']
|
||||
rulemanager.remove_rules(request, [obj_id],
|
||||
|
@ -23,6 +23,7 @@ from horizon import tables
|
||||
from openstack_dashboard import api
|
||||
from openstack_dashboard.dashboards.project.networks.ports \
|
||||
import tables as project_tables
|
||||
from openstack_dashboard import policy
|
||||
|
||||
LOG = logging.getLogger(__name__)
|
||||
|
||||
@ -36,7 +37,7 @@ def get_device_owner(port):
|
||||
return ' '
|
||||
|
||||
|
||||
class AddInterface(tables.LinkAction):
|
||||
class AddInterface(policy.PolicyTargetMixin, tables.LinkAction):
|
||||
name = "create"
|
||||
verbose_name = _("Add Interface")
|
||||
url = "horizon:project:routers:addinterface"
|
||||
@ -44,18 +45,12 @@ class AddInterface(tables.LinkAction):
|
||||
icon = "plus"
|
||||
policy_rules = (("network", "add_router_interface"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, 'tenant_id', None)
|
||||
return {"project_id": project_id}
|
||||
|
||||
def get_link_url(self, datum=None):
|
||||
router_id = self.table.kwargs['router_id']
|
||||
return reverse(self.url, args=(router_id,))
|
||||
|
||||
|
||||
class RemoveInterface(tables.DeleteAction):
|
||||
class RemoveInterface(policy.PolicyTargetMixin, tables.DeleteAction):
|
||||
@staticmethod
|
||||
def action_present(count):
|
||||
return ungettext_lazy(
|
||||
@ -75,12 +70,6 @@ class RemoveInterface(tables.DeleteAction):
|
||||
failure_url = 'horizon:project:routers:detail'
|
||||
policy_rules = (("network", "remove_router_interface"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, 'tenant_id', None)
|
||||
return {"project_id": project_id}
|
||||
|
||||
def delete(self, request, obj_id):
|
||||
try:
|
||||
router_id = self.table.kwargs['router_id']
|
||||
|
@ -24,12 +24,12 @@ from horizon import exceptions
|
||||
from horizon import messages
|
||||
from horizon import tables
|
||||
from openstack_dashboard import api
|
||||
|
||||
from openstack_dashboard import policy
|
||||
|
||||
LOG = logging.getLogger(__name__)
|
||||
|
||||
|
||||
class DeleteRouter(tables.DeleteAction):
|
||||
class DeleteRouter(policy.PolicyTargetMixin, tables.DeleteAction):
|
||||
@staticmethod
|
||||
def action_present(count):
|
||||
return ungettext_lazy(
|
||||
@ -49,12 +49,6 @@ class DeleteRouter(tables.DeleteAction):
|
||||
redirect_url = "horizon:project:routers:index"
|
||||
policy_rules = (("network", "delete_router"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, 'tenant_id', None)
|
||||
return {"project_id": project_id}
|
||||
|
||||
def delete(self, request, obj_id):
|
||||
obj = self.table.get_object_by_id(obj_id)
|
||||
name = self.table.get_object_display(obj)
|
||||
@ -84,7 +78,7 @@ class CreateRouter(tables.LinkAction):
|
||||
policy_rules = (("network", "create_router"),)
|
||||
|
||||
|
||||
class EditRouter(tables.LinkAction):
|
||||
class EditRouter(policy.PolicyTargetMixin, tables.LinkAction):
|
||||
name = "update"
|
||||
verbose_name = _("Edit Router")
|
||||
url = "horizon:project:routers:update"
|
||||
@ -92,14 +86,8 @@ class EditRouter(tables.LinkAction):
|
||||
icon = "pencil"
|
||||
policy_rules = (("network", "update_router"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, 'tenant_id', None)
|
||||
return {"project_id": project_id}
|
||||
|
||||
|
||||
class SetGateway(tables.LinkAction):
|
||||
class SetGateway(policy.PolicyTargetMixin, tables.LinkAction):
|
||||
name = "setgateway"
|
||||
verbose_name = _("Set Gateway")
|
||||
url = "horizon:project:routers:setgateway"
|
||||
@ -107,19 +95,13 @@ class SetGateway(tables.LinkAction):
|
||||
icon = "camera"
|
||||
policy_rules = (("network", "update_router"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, 'tenant_id', None)
|
||||
return {"project_id": project_id}
|
||||
|
||||
def allowed(self, request, datum=None):
|
||||
if datum.external_gateway_info:
|
||||
return False
|
||||
return True
|
||||
|
||||
|
||||
class ClearGateway(tables.BatchAction):
|
||||
class ClearGateway(policy.PolicyTargetMixin, tables.BatchAction):
|
||||
name = "cleargateway"
|
||||
action_present = _("Clear")
|
||||
action_past = _("Cleared")
|
||||
@ -129,12 +111,6 @@ class ClearGateway(tables.BatchAction):
|
||||
redirect_url = "horizon:project:routers:index"
|
||||
policy_rules = (("network", "update_router"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, 'tenant_id', None)
|
||||
return {"project_id": project_id}
|
||||
|
||||
def action(self, request, obj_id):
|
||||
obj = self.table.get_object_by_id(obj_id)
|
||||
name = self.table.get_object_display(obj)
|
||||
|
@ -23,6 +23,7 @@ from horizon import tables
|
||||
from openstack_dashboard import api
|
||||
from openstack_dashboard.api import base
|
||||
from openstack_dashboard.api import cinder
|
||||
from openstack_dashboard import policy
|
||||
|
||||
from openstack_dashboard.dashboards.project.volumes \
|
||||
.volumes import tables as volume_tables
|
||||
@ -40,39 +41,27 @@ class LaunchSnapshot(volume_tables.LaunchVolume):
|
||||
return "?".join([base_url, params])
|
||||
|
||||
|
||||
class DeleteVolumeSnapshot(tables.DeleteAction):
|
||||
class DeleteVolumeSnapshot(policy.PolicyTargetMixin, tables.DeleteAction):
|
||||
data_type_singular = _("Volume Snapshot")
|
||||
data_type_plural = _("Volume Snapshots")
|
||||
action_past = _("Scheduled deletion of %(data_type)s")
|
||||
policy_rules = (("volume", "volume:delete_snapshot"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum,
|
||||
"os-extended-snapshot-attributes:project_id",
|
||||
None)
|
||||
return {"project_id": project_id}
|
||||
policy_target_attrs = (("project_id",
|
||||
'os-extended-snapshot-attributes:project_id'),)
|
||||
|
||||
def delete(self, request, obj_id):
|
||||
api.cinder.volume_snapshot_delete(request, obj_id)
|
||||
|
||||
|
||||
class EditVolumeSnapshot(tables.LinkAction):
|
||||
class EditVolumeSnapshot(policy.PolicyTargetMixin, tables.LinkAction):
|
||||
name = "edit"
|
||||
verbose_name = _("Edit Snapshot")
|
||||
url = "horizon:project:volumes:snapshots:update"
|
||||
classes = ("ajax-modal",)
|
||||
icon = "pencil"
|
||||
policy_rules = (("volume", "volume:update_snapshot"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum,
|
||||
"os-extended-snapshot-attributes:project_id",
|
||||
None)
|
||||
return {"project_id": project_id}
|
||||
policy_target_attrs = (("project_id",
|
||||
'os-extended-snapshot-attributes:project_id'),)
|
||||
|
||||
def allowed(self, request, snapshot=None):
|
||||
return snapshot.status == "available"
|
||||
|
@ -33,6 +33,10 @@ from openstack_dashboard import policy
|
||||
DELETABLE_STATES = ("available", "error", "error_extending")
|
||||
|
||||
|
||||
class VolumePolicyTargetMixin(policy.PolicyTargetMixin):
|
||||
policy_target_attrs = (("project_id", 'os-vol-tenant-attr:tenant_id'),)
|
||||
|
||||
|
||||
class LaunchVolume(tables.LinkAction):
|
||||
name = "launch_volume"
|
||||
verbose_name = _("Launch as Instance")
|
||||
@ -55,18 +59,12 @@ class LaunchVolume(tables.LinkAction):
|
||||
return False
|
||||
|
||||
|
||||
class DeleteVolume(tables.DeleteAction):
|
||||
class DeleteVolume(VolumePolicyTargetMixin, tables.DeleteAction):
|
||||
data_type_singular = _("Volume")
|
||||
data_type_plural = _("Volumes")
|
||||
action_past = _("Scheduled deletion of %(data_type)s")
|
||||
policy_rules = (("volume", "volume:delete"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, "os-vol-tenant-attr:tenant_id", None)
|
||||
return {"project_id": project_id}
|
||||
|
||||
def delete(self, request, obj_id):
|
||||
obj = self.table.get_object_by_id(obj_id)
|
||||
name = self.table.get_object_display(obj)
|
||||
@ -121,19 +119,13 @@ class CreateVolume(tables.LinkAction):
|
||||
return HttpResponse(self.render())
|
||||
|
||||
|
||||
class ExtendVolume(tables.LinkAction):
|
||||
class ExtendVolume(VolumePolicyTargetMixin, tables.LinkAction):
|
||||
name = "extend"
|
||||
verbose_name = _("Extend Volume")
|
||||
url = "horizon:project:volumes:volumes:extend"
|
||||
classes = ("ajax-modal", "btn-extend")
|
||||
policy_rules = (("volume", "volume:extend"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, "os-vol-tenant-attr:tenant_id", None)
|
||||
return {"project_id": project_id}
|
||||
|
||||
def allowed(self, request, volume=None):
|
||||
return volume.status == "available"
|
||||
|
||||
@ -162,7 +154,7 @@ class EditAttachments(tables.LinkAction):
|
||||
return False
|
||||
|
||||
|
||||
class CreateSnapshot(tables.LinkAction):
|
||||
class CreateSnapshot(VolumePolicyTargetMixin, tables.LinkAction):
|
||||
name = "snapshots"
|
||||
verbose_name = _("Create Snapshot")
|
||||
url = "horizon:project:volumes:volumes:create_snapshot"
|
||||
@ -170,12 +162,6 @@ class CreateSnapshot(tables.LinkAction):
|
||||
icon = "camera"
|
||||
policy_rules = (("volume", "volume:create_snapshot"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, "os-vol-tenant-attr:tenant_id", None)
|
||||
return {"project_id": project_id}
|
||||
|
||||
def allowed(self, request, volume=None):
|
||||
try:
|
||||
limits = api.cinder.tenant_absolute_limits(request)
|
||||
@ -193,25 +179,19 @@ class CreateSnapshot(tables.LinkAction):
|
||||
return volume.status in ("available", "in-use")
|
||||
|
||||
|
||||
class CreateBackup(tables.LinkAction):
|
||||
class CreateBackup(VolumePolicyTargetMixin, tables.LinkAction):
|
||||
name = "backups"
|
||||
verbose_name = _("Create Backup")
|
||||
url = "horizon:project:volumes:volumes:create_backup"
|
||||
classes = ("ajax-modal",)
|
||||
policy_rules = (("volume", "backup:create"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, "os-vol-tenant-attr:tenant_id", None)
|
||||
return {"project_id": project_id}
|
||||
|
||||
def allowed(self, request, volume=None):
|
||||
return (cinder.volume_backup_supported(request) and
|
||||
volume.status == "available")
|
||||
|
||||
|
||||
class UploadToImage(tables.LinkAction):
|
||||
class UploadToImage(VolumePolicyTargetMixin, tables.LinkAction):
|
||||
name = "upload_to_image"
|
||||
verbose_name = _("Upload to Image")
|
||||
url = "horizon:project:volumes:volumes:upload_to_image"
|
||||
@ -219,13 +199,6 @@ class UploadToImage(tables.LinkAction):
|
||||
icon = "cloud-upload"
|
||||
policy_rules = (("volume", "volume:upload_to_image"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, "os-vol-tenant-attr:tenant_id", None)
|
||||
|
||||
return {"project_id": project_id}
|
||||
|
||||
def allowed(self, request, volume=None):
|
||||
has_image_service_perm = \
|
||||
request.user.has_perm('openstack.services.image')
|
||||
@ -234,7 +207,7 @@ class UploadToImage(tables.LinkAction):
|
||||
has_image_service_perm
|
||||
|
||||
|
||||
class EditVolume(tables.LinkAction):
|
||||
class EditVolume(VolumePolicyTargetMixin, tables.LinkAction):
|
||||
name = "edit"
|
||||
verbose_name = _("Edit Volume")
|
||||
url = "horizon:project:volumes:volumes:update"
|
||||
@ -242,17 +215,11 @@ class EditVolume(tables.LinkAction):
|
||||
icon = "pencil"
|
||||
policy_rules = (("volume", "volume:update"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, "os-vol-tenant-attr:tenant_id", None)
|
||||
return {"project_id": project_id}
|
||||
|
||||
def allowed(self, request, volume=None):
|
||||
return volume.status in ("available", "in-use")
|
||||
|
||||
|
||||
class RetypeVolume(tables.LinkAction):
|
||||
class RetypeVolume(VolumePolicyTargetMixin, tables.LinkAction):
|
||||
name = "retype"
|
||||
verbose_name = _("Change Volume Type")
|
||||
url = "horizon:project:volumes:volumes:retype"
|
||||
@ -260,13 +227,6 @@ class RetypeVolume(tables.LinkAction):
|
||||
icon = "pencil"
|
||||
policy_rules = (("volume", "volume:retype"),)
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
project_id = None
|
||||
if datum:
|
||||
project_id = getattr(datum, "os-vol-tenant-attr:tenant_id", None)
|
||||
|
||||
return {"project_id": project_id}
|
||||
|
||||
def allowed(self, request, volume=None):
|
||||
retype_supported = cinder.retype_supported()
|
||||
|
||||
|
@ -152,3 +152,29 @@ def _user_to_credentials(request, user):
|
||||
'is_admin': user.is_superuser,
|
||||
'roles': roles}
|
||||
return user._credentials
|
||||
|
||||
|
||||
class PolicyTargetMixin(object):
|
||||
"""Mixin that adds the get_policy_target function
|
||||
|
||||
policy_target_attrs - a tuple of tuples which defines
|
||||
the relationship between attributes in the policy
|
||||
target dict and attributes in the passed datum object.
|
||||
policy_target_attrs can be overwritten by sub-classes
|
||||
which do not use the default, so they can neatly define
|
||||
their policy target information, without overriding the
|
||||
entire get_policy_target function.
|
||||
"""
|
||||
|
||||
policy_target_attrs = (("project_id", "tenant_id"),
|
||||
("user_id", "user_id"),
|
||||
("domain_id", "domain_id"))
|
||||
|
||||
def get_policy_target(self, request, datum=None):
|
||||
policy_target = {}
|
||||
for policy_attr, datum_attr in self.policy_target_attrs:
|
||||
if datum:
|
||||
policy_target[policy_attr] = getattr(datum, datum_attr, None)
|
||||
else:
|
||||
policy_target[policy_attr] = None
|
||||
return policy_target
|
||||
|
Loading…
x
Reference in New Issue
Block a user