springrain使用shiro控制權限,配置filterChainDefinitions結合數據庫校驗權限。
我們在web.xml中配置一個全局過濾器,也就是在springrain配置的是一個spring bean的“shiroFilter“,在這個bean中可以根據訪問路徑在配置不同的過濾器,其中shiro默認自帶的過濾器如下:
Filter Name
Class
anon org.apache.shiro.web.filter.authc.AnonymousFilter
authc org.apache.shiro.web.filter.authc.FormAuthenticationFilter
authcBasic org.apache.shiro.web.filter.authc.BasicHttpAuthenticationFilter
logout org.apache.shiro.web.filter.authc.LogoutFilter
noSessionCreation org.apache.shiro.web.filter.session.NoSessionCreationFilter
perms org.apache.shiro.web.filter.authz.PermissionsAuthorizationFilter
port org.apache.shiro.web.filter.authz.PortFilter
rest org.apache.shiro.web.filter.authz.HttpMethodPermissionFilter
roles org.apache.shiro.web.filter.authz.RolesAuthorizationFilter
ssl org.apache.shiro.web.filter.authz.SslFilter
user org.apache.shiro.web.filter.authc.UserFilter
我們平時使用就是anno,任何人都可以訪問;authc:必須是登錄之后才能進行訪問,不包括remember me;user:登錄用戶才可以訪問,包含remember me;perms:指定過濾規則,這個一般是擴展使用,不會使用原生的;其中filterChainDefinitions 就是指定過濾規則的,一般公共配置使用配置文件,例如jss css img這些資源文件是不攔截的,相關業務的url配置到數據庫,有過濾器查詢數據庫進行權限判斷。
例:springrain的配置如下圖:
攔截器的優先級:從上到下,從左到右,如果有匹配的攔截器就會阻斷並返回,例如:訪問js/a.js,第一個攔截器anon符合,就返回true了,不在往下進行匹配了,注意最后一個攔截最后一句是 /**=user,frameperms 意思就是除了上面的那些,其他的所有都要經過 ,user和frameperms.如果沒有登陸 user就會阻斷,不會執行到frameperms.frameperms 就是我們自定義實現的過濾器,從數據庫中查詢用戶的權限,判斷當前用戶是否有權限訪問攔截的url.
其中具體攔截的工作流程是怎么樣的呢?
1:認證和授權的 realm.例如springrain擴展的shiroDbRealm,在doGetAuthorizationInfo授權方法里
- // 添加角色及權限信息
- SimpleAuthorizationInfo sazi = new SimpleAuthorizationInfo();
- try {
- sazi.addRoles(userRoleMenuService.getRolesAsString(userId));
- sazi.addStringPermissions(userRoleMenuService
- .getPermissionsAsString(userId));
- } catch (Exception e) {
- logger.error(e);
- }
- return sazi;
sazi.addStringPermissions:獲取當前用戶的所有權限,springrain中的權限就是url,所以在springrain中這就是一個url的集合
我們的攔截器每次校驗權限都會調用doGetAuthorizationInfo,獲取當前用戶的所有權限.
我們的權限攔截器 只要判斷當前用戶訪問的url是否在他的權限集合內就可以了,例如 springrain中frameperms 的校驗url權限:
- //會調用realm的doGetAuthorizationInfo授權方法
- permitted= subject.isPermitted(uri);