您的位置:首页 > 其它

shiro多realm配置(可区分不同类型用户)

2017-06-05 22:54 141 查看
由于项目中需要用到shiro,但是用户来自不同的三张表,需要根据token判断不同类型的用户,但是shiro得token不支持带类型的参数,所以需要重写token及认证器

1.自定义token

/**
* 自定义带用户类型token
* @author Sunny
*/
public class UsernamePasswordByUserTypeToken extends UsernamePasswordToken {
private static final long serialVersionUID = -7638434498222500528L;

/*
* 用户类型
* 1:积分后台用户(后台管理员)
* 2:积分兑换端用户(店长店员)
* 3:积分验证端用户(第三方合作店铺)
*/
private String userType;

public String getUserType() {
return userType;
}

public void setUserType(String userType) {
this.userType = userType;
}

public UsernamePasswordByUserTypeToken(String username, String password, String userType) {
super(username, password);
this.userType = userType;
}
}


2.自定义认证器

/**
* 自定义认证器
*
* @author Sunny
*/
public class PointRealmAuthenticator extends ModularRealmAuthenticator {
/**
* 存放realm
*/
private Map<String, Object> definedRealms;

public void setDefinedRealms(Map<String, Object> definedRealms) {
this.definedRealms = definedRealms;
}

/**
* 根据用户类型判断使用哪个Realm
*/
@Override
protected AuthenticationInfo doAuthenticate(AuthenticationToken authenticationToken)
throws AuthenticationException {
super.assertRealmsConfigured();
Realm realm = null;
// 使用自定义Token
UsernamePasswordByUserTypeToken token = (UsernamePasswordByUserTypeToken) authenticationToken;
// 判断用户类型
if ("1".equals(token.getUserType())) {
realm = (Realm) this.definedRealms.get("pointSysShiroDbRealm");
} else if ("2".equals(token.getUserType())) {
realm = (Realm) this.definedRealms.get("pointExchangeShiroDbRealm");
} else if ("3".equals(token.getUserType())) {
realm = (Realm) this.definedRealms.get("pointValidShiroDbRealm");
}
return this.doSingleRealmAuthentication(realm, authenticationToken);
}
}

3.配置shiro xml文件

<!-- 配置 Shiro 的 SecurityManager 实例 -->
<bean id="securityManager" class="org.apache.shiro.web.mgt.DefaultWebSecurityManager">
<property name="authenticator" ref="pointRealmAuthenticator" />
<!-- 单Realm配置废弃 -->
<!-- <property name="realm" ref="shiroDbRealm" /> -->
<!-- 多Realm注入 -->
<property name="realms">
<list>
<ref bean="pointSysShiroDbRealm" />
<ref bean="pointExchangeShiroDbRealm" />
<ref bean="pointValidShiroDbRealm" />
</list>
</property>
<property name="cacheManager" ref="shiroEhcacheManager" />
</bean>

<!-- 项目自定义Authenticator -->
<bean id="pointRealmAuthenticator"
class="org.zmshop.common.shiro.authenticator.PointRealmAuthenticator">
<!-- realmMap -->
<property name="definedRealms">
<map>
<entry key="pointSysShiroDbRealm" value-ref="pointSysShiroDbRealm" />
<entry key="pointExchangeShiroDbRealm" value-ref="pointExchangeShiroDbRealm" />
<entry key="pointValidShiroDbRealm" value-ref="pointValidShiroDbRealm" />
</map>
</property>
</bean>

<!-- 项目自定义的Realm -->
<!-- 积分后台用户(后台管理员)Realm -->
<bean id="pointSysShiroDbRealm" class="org.zmshop.common.shiro.realm.PointSysShiroDbRealm">
<property name="maUserService" ref="maUserServiceImpl" />
<property name="baUserGradeService" ref="baUserGradeServiceImpl" />
</bean>
<!-- 积分兑换端用户(店长店员)Realm -->
<bean id="pointExchangeShiroDbRealm" class="org.zmshop.common.shiro.realm.PointExchangeShiroDbRealm">
<property name="baUserService" ref="baUserServiceImpl" />
<property name="baUserSubService" ref="baUserSubServiceImpl" />
<property name="stClerkService" ref="stClerkServiceImpl" />
<property name="baUserGradeService" ref="baUserGradeServiceImpl" />
<property name="stMainService" ref="stMainServiceImpl" />
</bean>
<!-- 积分验证端用户(第三方合作店铺)Realm -->
<bean id="pointValidShiroDbRealm" class="org.zmshop.common.shiro.realm.PointValidShiroDbRealm">
<property name="ebtPointEmployeeService" ref="ebtPointEmployeeServiceImpl" />
<property name="baUserGradeService" ref="baUserGradeServiceImpl" />
</bean>
4.Realm文件需注意事项
public class PointExchangeShiroDbRealm extends AuthorizingRealm {
/**
* 身份验证回调函数,登录时调用
*/
@Override
protected AuthenticationInfo doGetAuthenticationInfo(AuthenticationToken authcToken)
throws AuthenticationException {
//具体登录判断逻辑
return xxx;
}

/**
* 授权查询回调函数,进行鉴权但缓存中无用户的授权信息时调用
* 多realm该方法会在多个realm之间调用,所以需要判断当前用户是否是当前类中的shirouser对象[其他realm一样]
*/
@Override
protected AuthorizationInfo doGetAuthorizationInfo(PrincipalCollection principals) {
// 判断是否是当前用户登录的对象
if (principals == null || !(principals.getPrimaryPrincipal() instanceof ShiroUser)) {
return null;
}
return xxx;
}

/**
* 自定义Authentication对象,使得Subject除了携带用户的登录名外还可以携带更多信息.
*/
public class ShiroUser implements Serializable {
private static final long serialVersionUID = 7240137316895366700L;
}
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: 
相关文章推荐