shiro权限学习结合Spring框架
环境搭建导入shiro包及spring支持shiro的包web.xml的关于shiro的配置创建自定的myRealm配置application-context.xml文件
调用shiro权限shiro前端的应用,页面显示
环境搭建
导入shiro包及spring支持shiro的包
<dependency>
<groupId>org.apache.shiro
</groupId>
<artifactId>shiro-core
</artifactId>
<version>1.4.0
</version>
</dependency>
<dependency>
<groupId>org.apache.shiro
</groupId>
<artifactId>shiro-web
</artifactId>
<version>1.4.0
</version>
</dependency>
<dependency>
<groupId>org.apache.shiro
</groupId>
<artifactId>shiro-spring
</artifactId>
<version>1.4.0
</version>
</dependency>
<dependency>
<groupId>commons-beanutils
</groupId>
<artifactId>commons-beanutils
</artifactId>
<version>1.9.3
</version>
</dependency>
web.xml的关于shiro的配置
<filter>
<filter-name>shiroFilter
</filter-name>
<filter-class>org.springframework.web.filter.DelegatingFilterProxy
</filter-class>
</filter>
<filter-mapping>
<filter-name>shiroFilter
</filter-name>
<url-pattern>/*
</url-pattern>
<dispatcher>REQUEST
</dispatcher>
<dispatcher>FORWARD
</dispatcher>
<dispatcher>INCLUDE
</dispatcher>
<dispatcher>ERROR
</dispatcher>
</filter-mapping>
创建自定的myRealm
创建的myrealm需要继承org.apache.shiro.realm.AuthorizingRealm类,并重写doGetAuthorizationInfo和doGetAuthenticationInfo方法参数类型为AuthenticationToken是认证,用来判断登录成功还是失败,失败返回null参数类行为PrincipalCollection 是授权,用来赋予登录的用户相应的权限
import org
.apache
.shiro
.authc
.AuthenticationException
;
import org
.apache
.shiro
.authc
.AuthenticationInfo
;
import org
.apache
.shiro
.authc
.AuthenticationToken
;
import org
.apache
.shiro
.authc
.SimpleAuthenticationInfo
;
import org
.apache
.shiro
.authz
.AuthorizationInfo
;
import org
.apache
.shiro
.authz
.SimpleAuthorizationInfo
;
import org
.apache
.shiro
.realm
.AuthorizingRealm
;
import org
.apache
.shiro
.subject
.PrincipalCollection
;
import org
.springframework
.beans
.factory
.annotation
.Autowired
;
public class MyRealm extends AuthorizingRealm {
@Autowired
private UserService userService
;
@Autowired
private PermissionService permissionService
;
@Override
protected AuthorizationInfo
doGetAuthorizationInfo(PrincipalCollection p
) {
String username
= (String
) p
.getPrimaryPrincipal();
User user
= new User();
user
.setUsername(username
);
List
<User> users
= userService
.find(user
);
Integer roleId
= users
.get(0).getRoles().getId();
List
<Permission> resourceUrl
= permissionService
.findResourceUrl(roleId
);
SimpleAuthorizationInfo info
= new SimpleAuthorizationInfo();
for (int i
= 0; i
<resourceUrl
.size();i
++){
info
.addStringPermission(resourceUrl
.get(i
).getResourceUrl());
}
return info
;
}
@Override
protected AuthenticationInfo
doGetAuthenticationInfo(AuthenticationToken token
) throws AuthenticationException
{
String username
= (String
)token
.getPrincipal();
User user
= new User();
user
.setUsername(username
);
List
<User> users
= userService
.find(user
);
if(users
.size() == 1){
String password
= users
.get(0).getPassword();
SimpleAuthenticationInfo myRealm
= new SimpleAuthenticationInfo(username
, password
, "myRealm");
return myRealm
;
}
return null
;
}
}
配置application-context.xml文件
将创建的myRealm交给spring管理将DefaultWebSecurityManager交给spring管理,将myRealm注入到DefaultWebSecurityManager中创建shiro工厂,并将DefaultWebSecurityManager注入到工厂类中,并设置拦截规则重要参数:
authc 需要登录认证logout 退出,注销perms[] 授权roles[] 授角色(我认为角色就是一组权限的集合)loginUrl 登录页面的url
<bean id="myRealm" class="com.hospital.realm.MyRealm"></bean>
<bean id="securityManager" class="org.apache.shiro.web.mgt.DefaultWebSecurityManager">
<property name="realm">
<ref bean="myRealm"></ref>
</property>
</bean>
<bean id="shiroFilter" class="org.apache.shiro.spring.web.ShiroFilterFactoryBean">
<property name="securityManager">
<ref bean="securityManager"></ref>
</property>
<property name="loginUrl" value="/login.action"></property>
<property name="unauthorizedUrl" value="/error.jsp"></property>
<property name="filterChainDefinitions">
<value>
/logout = logout
/error.jsp = anon
/user/* = authc,perms[/user/forward]
/role/* = authc,perms[/roles/forward]
/registration/* = authc,perms[/registration/forward]
/permission/* = authc,perms[/permission/forward]
/hospital/* = authc,perms[/hospitalization/forward]
/home/* = authc
/drug/* = authc,perms[/drug/forward]
/doctor/* = authc,perms[/doctor/forward]
</value>
</property>
</bean>
调用shiro权限
登录页面之后,后端获取登录页面传来的用户名和密码,将用户名和密码传送到UsernamePasswordToken这个类中,就可以调用shiro 在调用过程中,有两个比较重要的类需要掌握
org.apache.shiro.subject.Subject 用于进行授权和认证,如果认证失败会有异常抛出,需要捕获异常org.apache.shiro.authc.UsernamePasswordToken 用于调用自定义的myRealm
import org
.apache
.shiro
.SecurityUtils
;
import org
.apache
.shiro
.authc
.UsernamePasswordToken
;
import org
.apache
.shiro
.subject
.Subject
;
import org
.springframework
.beans
.factory
.annotation
.Autowired
;
import org
.springframework
.stereotype
.Controller
;
import org
.springframework
.ui
.Model
;
import org
.springframework
.web
.bind
.annotation
.RequestMapping
;
import org
.springframework
.web
.bind
.annotation
.RequestMethod
;
@Controller
public class LoginController {
@Autowired
private UserService userService
;
@RequestMapping(value
= "/login.action",method
= RequestMethod
.GET
)
public String
hospitalLogin(){
return "index";
}
@RequestMapping(value
= "/login.action",method
= RequestMethod
.POST
)
public String
login(User user
, Model model
) {
Subject subject
= SecurityUtils
.getSubject();
String username
= user
.getUsername();
String password
= user
.getPassword();
UsernamePasswordToken token
= new UsernamePasswordToken(username
, password
);
String error
= null
;
try {
subject
.login(token
);
} catch (Exception e
) {
error
= "用户名或密码错误";
model
.addAttribute("error", error
);
return "index";
}
if (error
== null
) {
List
<User> users
= userService
.find(user
);
User user1
= users
.get(0);
model
.addAttribute("user",user1
);
return "/home/home";
}
return null
;
}
}
shiro前端的应用,页面显示
导包
<%@ taglib prefix="shiro" uri="http://shiro.apache.org/tags" %>
代码实现
<body>
<%--shiro获取登录用户名--%>
<h1>hello-->
<shiro:principal></shiro:principal></h1>
<%--当没有登录时会显示,登录后隐藏--%>
<shiro:guest>
<a href="/Demo33/admin">用户登录
</a>
</shiro:guest>
<%--当没有登录时不会显示,登录后按照以下权限配置显示--%>
<shiro:user>
<a href="user/index.jsp">用户列表
</a>
<%--是否拥有用户增加权限,没有就不显示--%>
<shiro:hasPermission name="user:add">
<a href="user/add.jsp">用户增加
</a>
</shiro:hasPermission>
<%--是否是角色admin,没有就不显示--%>
<shiro:hasRole name="admin">
<a href="/Demo33/department">部门列表
</a>
</shiro:hasRole>
<a href="/Demo33/logout">退出系统
</a>
</shiro:user>
</body>