コード例 #1
0
ファイル: state_changes.py プロジェクト: glizzan/concord
class AddRoleToPermissionStateChange(BaseStateChange):
    """State change to add a role to a permission."""

    descriptive_text = {
        "verb": "add",
        "default_string": "role to permission",
        "detail_string": "role {role_name} to permission",
        "preposition": "for"
    }

    section = "Permissions"
    allowable_targets = [PermissionsItem]
    settable_classes = ["all_models"]

    role_name = field_utils.RoleField(label="Role to add", required=True)

    def validate(self, actor, target):
        community_owner = target.get_owner()
        if not community_owner.roles.is_role(self.role_name):
            raise ValidationError(
                f"{self.role_name} is not a role and so can't be set on permission"
            )

    def implement(self, actor, target, **kwargs):
        target.add_role_to_permission(role=self.role_name)
        target.save()
        return target
コード例 #2
0
ファイル: state_changes.py プロジェクト: glizzan/concord
class RemoveRoleFromPermissionStateChange(BaseStateChange):
    """State change to remove a role from a permission."""

    descriptive_text = {
        "verb": "remove",
        "default_string": "role from permission",
        "detail_string": "role {role_name} from permission",
        "preposition": "for"
    }

    section = "Permissions"
    linked_filters = ["RoleMatchesFilter"]
    allowable_targets = [PermissionsItem]
    settable_classes = ["all_models"]

    role_name = field_utils.RoleField(label="Role to remove", required=True)

    def validate(self, actor, target):
        if not target.roles.role_name_in_list(self.role_name):
            raise ValidationError(
                f"{self.role_name} isn't a role on this permission so can't be removed"
            )

    def implement(self, actor, target, **kwargs):
        target.remove_role_from_permission(role=self.role_name)
        target.save()
        return target
コード例 #3
0
class RoleMatchesFilter(Filter):
    descriptive_name = "the role's name is a specific value"
    configured_name = "the role's name is '{role_name}'"
    linked = True

    role_name = field_utils.RoleField(label="Role to match", required=True)

    def check(self, *, action, **kwargs):
        return action.change.role_name == self.role_name, f"the role name does not match {self.role_name}"
コード例 #4
0
ファイル: state_changes.py プロジェクト: glizzan/concord
class RemovePeopleFromRoleStateChange(BaseStateChange):
    """State change to remove people from role in Community."""

    descriptive_text = {
        "verb": "remove",
        "default_string": "people from role",
        "detail_string": "people {people_to_remove} from role '{role_name}'",
        "preposition": "in"
    }

    section = "Community"
    allowable_targets = ["all_community_models"]

    role_name = field_utils.RoleField(label="Role to remove people from", required=True)
    people_to_remove = field_utils.ActorListField(label="People to remove from role", required=True)

    def is_conditionally_foundational(self, action):
        """If role_name is owner or governor role, should should be treated as a conditional
        change."""
        if self.role_name in action.target.roles.get_owners()["roles"]:
            return True
        if self.role_name in action.target.roles.get_governors()["roles"]:
            return True
        return False

    def validate(self, actor, target):
        """When removing people from a role, we must check that doing so does not leave us
        without any owners."""

        if self.role_name not in target.roles.get_owners()["roles"]:
            return  # this isn't an owner role

        if len(self.people_to_remove) < len(target.roles.get_users_given_role(self.role_name)):
            return  # removing these users will not result in empty role

        if len(target.roles.get_owners()["actors"]) > 0:
            return  # community has individual actor owners so it doesn't need roles

        for role in target.roles.get_owners()["roles"]:
            if role == self.role_name:
                continue
            actors = target.roles.get_users_given_role(role)
            if len(actors) > 0:
                return  # there are other owner roles with actors specified

        raise ValidationError("Cannot remove everyone from this role as " +
                              "doing so would leave the community without an owner")

    def implement(self, actor, target, **kwargs):
        target.roles.remove_people_from_role(self.role_name, self.people_to_remove)
        target.save()
        return target
コード例 #5
0
ファイル: state_changes.py プロジェクト: glizzan/concord
class RemoveRoleStateChange(BaseStateChange):
    """State change to remove role from Community."""

    descriptive_text = {
        "verb": "remove",
        "default_string": "role from community",
        "detail_string": "role {role_name}",
        "preposition": "from"
    }

    section = "Community"
    allowable_targets = ["all_community_models"]

    role_name = field_utils.RoleField(label="Role to remove from community", required=True)

    def role_in_permissions(self, permission, actor):
        """Checks for role in permission and returns True if it exists.  Checks in permissions
        which are nested on this permission as well."""
        role_references = []
        if permission.has_role(role=self.role_name):
            role_references.append(permission)
        client = Client(actor=actor, target=permission)
        for permission in client.PermissionResource.get_all_permissions():
            role_references += self.role_in_permissions(permission, actor)
        return role_references

    def validate(self, actor, target):
        """A role cannot be deleted without removing it from the permissions it's referenced in, and
        without removing it from owner and governor roles if it is there."""

        role_references = []
        client = Client(actor=actor, target=target)
        for permission in client.PermissionResource.get_all_permissions():
            role_references += self.role_in_permissions(permission, actor)

        if len(role_references) > 0:
            permission_string = ", ".join([str(permission.pk) for permission in role_references])
            raise ValidationError(f"Role cannot be deleted until it is removed from permissions: {permission_string}")

        if self.role_name in target.roles.get_owners()["roles"]:
            raise ValidationError("Cannot remove role with ownership privileges")
        if self.role_name in target.roles.get_governors()["roles"]:
            raise ValidationError("Cannot remove role with governorship privileges")

    def implement(self, actor, target, **kwargs):
        target.roles.remove_role(self.role_name)
        target.save()
        return target
コード例 #6
0
ファイル: state_changes.py プロジェクト: glizzan/concord
class AddPeopleToRoleStateChange(BaseStateChange):
    """State change to add people to role in Community."""

    descriptive_text = {
        "verb": "add",
        "default_string": "people to role",
        "detail_string": "people {people_to_add} to role '{role_name}'",
        "preposition": "in"
    }

    section = "Community"
    allowable_targets = ["all_community_models"]

    role_name = field_utils.RoleField(label="Role to add people to", required=True)
    people_to_add = field_utils.ActorListField(label="People to add to role", required=True)

    linked_filters = ["RoleMatchesFilter"]

    def is_conditionally_foundational(self, action):
        """If role_name is owner or governor role, should should be treated as a conditional change."""
        if self.role_name in action.target.roles.get_owners()["roles"]:
            return True
        if self.role_name in action.target.roles.get_governors()["roles"]:
            return True
        return False

    def validate(self, actor, target):
        if not isinstance(self.role_name, str):
            raise ValidationError(f"Role must be type str, not {str(type(self.role_name))}")
        if not target.roles.is_role(self.role_name):
            raise ValidationError(f"Role {self.role_name} does not exist")
        people_already_in_role = []
        for person in self.people_to_add:
            if target.roles.has_specific_role(self.role_name, person):
                people_already_in_role.append(str(person))
        if people_already_in_role:
            raise ValidationError(f"Users {list_to_text(people_already_in_role)} already in role {self.role_name}")

    def implement(self, actor, target, **kwargs):
        target.roles.add_people_to_role(self.role_name, self.people_to_add)
        target.save()
        return target
コード例 #7
0
ファイル: state_changes.py プロジェクト: glizzan/concord
class AddRoleStateChange(BaseStateChange):
    """State change to add role to Community."""

    descriptive_text = {
        "verb": "add",
        "default_string": "role to community",
        "detail_string": "role {role_name} to community",
    }

    section = "Community"
    allowable_targets = ["all_community_models"]

    role_name = field_utils.RoleField(label="Role to add to community", required=True)

    def validate(self, actor, target):
        if self.role_name in ["members", "governors", "owners"]:
            raise ValidationError("Role name cannot be one of protected names: members, governors, owners.")
        if target.roles.is_role(self.role_name):
            raise ValidationError("The role " + self.role_name + " already exists.")

    def implement(self, actor, target, **kwargs):
        target.roles.add_role(self.role_name)
        target.save()
        return target