我正试图以下一种方式动态更新用户凭据:当de admin按下按钮时,新角色将添加到数据库中的每个标准用户。断开连接的用户没有问题,因为当他们登录时,自定义身份验证提供程序从db加载他的所有角色,但是已登录的用户无法访问新的可用部分,因为身份验证对象没有新角色。为了解决这个问题,我尝试了很多机制,但是我看到的正确且不那么具有侵入性的是使用了听众。以下是这样的想法:当管理员按下按钮时,将更新数据库并触发和处理新的自定义事件。理论上,此事件会为每个活动用户和IT人员生成重新认证,仅针对触发事件的用户(管理员)。 现在,我想知道为什么会这样,为什么事件不适用于每个SecurityContextHolder而只适用于触发它的人。我虽然问题是在bean的范围内,所以我给它一个会话范围,但抛出一个错误。如果有人可以帮助我,请 这是正确的代码
我的调度程序servlet
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:p="http://www.springframework.org/schema/p"
xmlns:mvc="http://www.springframework.org/schema/mvc"
xmlns:context="http://www.springframework.org/schema/context"
xmlns:aop="http://www.springframework.org/schema/aop"
xmlns:tx="http://www.springframework.org/schema/tx"
xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-3.1.xsd
http://www.springframework.org/schema/mvc http://www.springframework.org/schema/mvc/spring-mvc-3.1.xsd
http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-3.1.xsd
http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop-3.1.xsd
http://www.springframework.org/schema/tx http://www.springframework.org/schema/tx/spring-tx-3.1.xsd">
<context:component-scan base-package="printer">
<context:include-filter type="annotation" expression="org.springframework.stereotype.Controller"/>
<context:exclude-filter type="annotation" expression="org.springframework.stereotype.Service"/>
</context:component-scan>
<bean id="viewResolver"
class="org.springframework.web.servlet.view.InternalResourceViewResolver"
p:prefix="/WEB-INF/jsp/"
p:suffix=".jsp" />
//nothing that matters here
<bean id="reauthenticating" class="printer.Security.Events.ReauthenticatingEventsPostProcessor" scope="prototype"/>
事件
public class ReauthenticatingUseronRoleChangeEvent extends ApplicationEvent {
private static final long serialVersionUID = 1L;
private String roleType;
private String actionType;
public ReauthenticatingUseronRoleChangeEvent(Object source,String roleType, String actionType) {
super(source);
this.roleType = roleType;
this.actionType = actionType;
}
public String getRoleType() {
return roleType;
}
public String getActionType() {
return actionType;
}
事件触发器是我的UserService
public class UserService_Impl implements UserService,ApplicationEventPublisherAware{
@Override
public void publishAccessToDownloadEvent() {
.....
enter code here
@Override
public void publishAccessToDownloadEvent() {
publisher.publishEvent(new ReauthenticatingUseronRoleChangeEvent(this, "ROLE_DOWNLOAD", "add"));
}
这是事件监听器。这是我迷路的地方,并不认为它是为每个用户执行的????
public class ReauthenticatingEventsPostProcessor implements ApplicationListener<ReauthenticatingUseronRoleChangeEvent> {
@Autowired
@Qualifier("userDao")
UserDAO userDao;
@Override
public void onApplicationEvent(ReauthenticatingUseronRoleChangeEvent e) {
Authentication auth = SecurityContextHolder.getContext().getAuthentication();
List<GrantedAuthority> authorities = new ArrayList<GrantedAuthority> (auth.getAuthorities());
Role r=new Role();
r.setRole(e.getRoleType());
authorities.add(r);
Authentication newAuth = new UsernamePasswordAuthenticationToken(auth.getPrincipal(),auth.getCredentials(),authorities);
SecurityContextHolder.getContext().setAuthentication(newAuth);
}
}
@Override
public void setApplicationEventPublisher(ApplicationEventPublisher aep) {
this.publisher=aep;}
正如我上面所说,听众工作得很好,就像没有那样。而是为每个用户执行他,为仅触发事件的用户执行此操作。