Koosa 1.0.1

Koosa 1.0.1

Mostafa Abdellateef 维护。



Koosa 1.0.1

Koosa    Build Status Coverage Status

Swift 的简单基于角色的访问控制

查看这篇博客文章以了解完整解释和更多详情: Swift 的访问控制管理

示例

代码 行动中
// Anyone can browse group, if it is public
Visitor.shouldBeAbleTo(BrowseGroup.action).when {
    guard let browseAction = $1 as? BrowseGroup else { return false }
    return browseAction.group.isPublicGroup
}

// Member can browse his groups + public groups
GroupMemberUser.shouldBeAbleTo(BrowseGroup.action).when {
    guard let groupMember = $0 as? GroupMember,
        let browseAction = $1 as? BrowseGroup else { return false }
    return groupMember.groupNumber == browseAction.group.groupNumber
}

// Member can post his groups 
GroupMemberUser.shouldBeAbleTo(PostToGroup.action).when {
    guard let groupMember = $0 as? GroupMember,
        let postAction = $1 as? PostToGroup else { return false }
    return groupMember.groupNumber == postAction.group.groupNumber
}

// Admin class extends Member + ability to delete
GroupAdminUser.shouldBeAbleTo(DeleteGroup.action).when {
    guard let groupAdmin = $0 as? GroupAdmin,
        let deleteAction = $1 as? DeleteGroup else { return false }
    return groupAdmin.groupNumber == deleteAction.group.groupNumber
}

// SuperAdmin can do everything
_ = SuperAdminUser.shouldBeAbleTo(BrowseGroup.action)
_ = SuperAdminUser.shouldBeAbleTo(DeleteGroup.action)
_ = SuperAdminUser.shouldBeAbleTo(PostToGroup.action)

用法

  1. 首先将您的需求中的每个角色映射到一个扩展自协议 Role 的协议或扩展此协议的协议。注意,您可以使用协议继承来建模角色层次结构。
protocol GroupMember: Role {
    var groupNumber: Int {set get}
}
protocol GroupAdmin: GroupMember { }
  1. 将您的动作建模到符合协议 Action 的类/结构体。
struct BrowseGroup: Action {
    let group: Group
    
    init() {  // required default initializer
        group = Group(groupNumber: -1, isPublicGroup: false) // default froup
    }
    
    init(group: Group) {
        self.group = group
    }
}
  1. 使用角色协议创建具体的角色类。
class GroupAdminUser: User, GroupAdmin {
    var groupNumber: Int
    init(name: String, age: Int, groupNumber: Int) {
        self.groupNumber = groupNumber
        super.init(name: name, age: age)
    }
    
    override required init() {
        self.groupNumber = -1
        super.init()
    }
}
  1. 添加策略。
GroupMemberUser.shouldBeAbleTo(BrowseGroup.action).when {
    guard let groupMember = $0 as? GroupMember,
        let browseAction = $1 as? BrowseGroup else { return false }
    return groupMember.groupNumber == browseAction.group.groupNumber
}
GroupAdminUser.shouldBeAbleTo(DeleteGroup.action).when {
    guard let groupAdmin = $0 as? GroupAdminUser,
        let deleteAction = $1 as? DeleteGroup else {
            return false
    }
    return groupAdmin.groupNumber == deleteAction.group.groupNumber
}
_ = SuperAdminUser.shouldBeAbleTo(BrowseGroup.action)
  1. 现在,您可以验证任何用户是否可以执行任何动作。
let member1 = GroupMemberUser(name: "member1", age: 18, groupNumber: 1)
let admin2 = GroupAdminUser(name: "admin2", age: 22, groupNumber: 2)
let group1 = Group(groupNumber: 1, isPublicGroup: false)
let group2 = Group(groupNumber: 2, isPublicGroup: false)
member1.can(BrowseGroup(group: group1) // true
member1.can(BrowseGroup(group: group2) // false
admin2.can(BrowseGroup(group: group1) // true: GroupAdmin inherits BrowseGroup permission from GroupMember
admin2.can(DeleteGroup(group: group2) // true
admin2.can(DeleteGroup(group: group1) // false

安装

Koosa可以使用CocoaPods进行安装

use_frameworks!
pod 'Koosa'

授权

MIT