授 权
授权实质上就是访问控制 - 控制用户能够访问应用中的哪些内容,比如资源、Web页面等等。多数用户执行访问控制是通过使用诸如角色和权限这类概念完成的。也就是说,通常用户允许或不允许做的事情是根据分配给他们的角色或权限决定的。那么,通过检查这些角色和权限,你的应用程序就可以控制哪些功能是可以暴露的。如你期望的,Subject API让你可以很容易的执行角色和权限检查。如清单7中的代码片段所示:如何检查Subject被分配了某个角色:
列表7. 角色检查
//显示‘Create User’按钮
} else {
//按钮置灰?
}
如你所见,你的应用程序可基于访问控制检查打开或关闭某些功能。
权限检查是执行授权的另一种方法。上例中的角色检查有个很大的缺陷:你无法在运行时增删角色。角色名字在这里是硬编码,所以,如果你修改了角色名字或配置,你的代码就会乱套!如果你需要在运行时改变角色含义,或想要增删角色,你必须另辟蹊径。
为此,Shiro支持了权限(permissions)概念。权限是功能的原始表述,如‘开门’,‘创建一个博文’,‘删除‘jsmith’用户’等。通过让权限反映应用的原始功能,在改变应用功能时,你只需要改变权限检查。进而,你可以在运行时按需将权限分配给角色或用户。
如清单8中,我们重写了之前的用户检查,取而代之使用权限检查。
清单8. 权限检查
//显示‘Create User’按钮
} else {
//按钮置灰?
}
这样,任何具有“user:create”权限的角色或用户都可以点击‘Create User’按钮,并且这些角色和指派甚至可以在运行时改变,这给你提供了一个非常灵活的安全模型。
“user:create”字符串是一个权限字符串的例子,它遵循特定的解析惯例。Shiro借助它的WildcardPermission支持这种开箱即用的惯例。尽管这超出了本文的范围,你会看到在创建安全策略时,WildcardPermission非常灵活,甚至支持像实例级别访问控制这样的功能。
清单9. 实例级别的权限检查
//删除‘jsmith’用户
} else {
//不删除‘jsmith’
}
该例表明,你可以对你需要的单个资源进行访问控制,甚至深入到非常细粒度的实例级别。如果愿意,你甚至还可以发明自己的权限语法。参见Shiro Permission文档可以了解更多内容。最后,就像使用认证那样,上述调用最终会转向SecurityManager,它会咨询Realm做出自己的访问控制决定。必要时,还允许单个Realm同时响应认证和授权操作。
以上就是对Shiro授权功能的简要概述。虽然多数安全框架止于授权和认证,但Shiro提供了更多功能。下面,我们将谈谈Shiro的高级会话管理功能。