我有一个Spring项目,我在Login成功时为Audit实现了一个函数。该功能有效,但我需要在登录成功时写入数据库。我的豆是:
CustomLoginSucessHandler.java
public class CustomLoginSucessHandler extends SavedRequestAwareAuthenticationSuccessHandler {
final static Logger log = LoggerFactory.getLogger(CustomLoginSucessHandler.class);
@Autowired
private UserService userService;
@Override
public void onAuthenticationSuccess(HttpServletRequest request,
HttpServletResponse response, Authentication authentication)
throws ServletException, IOException {
final String userName = authentication.getName();
log.debug("User name is: " + userName);
final User user = userService.getUser(userName);
final Date date = new Date();
final Timestamp timeStamp = new Timestamp(date.getTime());
user.setLastLogin(timeStamp);
userService.saveUser(user);
log.debug("User Last Login update to " + timeStamp);
super.onAuthenticationSuccess(request, response, authentication);
}
}
请注意,我有@Autowired
注释,但它始终返回null
。
我已尝试使用@Service
和@Configurable
进行注释,但到目前为止还没有成功。
堆栈跟踪
java.lang.NullPointerException
com.opessoftware.fatca.web.util.CustomLoginSucessHandler.onAuthenticationSuccess(CustomLoginSucessHandler.java:33)
org.springframework.security.web.authentication.AbstractAuthenticationProcessingFilter.successfulAuthentication(AbstractAuthenticationProcessingFilter.java:331)
org.springframework.security.web.authentication.AbstractAuthenticationProcessingFilter.doFilter(AbstractAuthenticationProcessingFilter.java:245)
org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:330)
org.springframework.security.web.authentication.logout.LogoutFilter.doFilter(LogoutFilter.java:120)
org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:330)
org.springframework.security.web.csrf.CsrfFilter.doFilterInternal(CsrfFilter.java:96)
org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:107)
org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:330)
org.springframework.security.web.header.HeaderWriterFilter.doFilterInternal(HeaderWriterFilter.java:64)
org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:107)
org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:330)
org.springframework.security.web.context.SecurityContextPersistenceFilter.doFilter(SecurityContextPersistenceFilter.java:91)
org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:330)
org.springframework.security.web.context.request.async.WebAsyncManagerIntegrationFilter.doFilterInternal(WebAsyncManagerIntegrationFilter.java:53)
org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:107)
org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:330)
org.springframework.security.web.FilterChainProxy.doFilterInternal(FilterChainProxy.java:213)
org.springframework.security.web.FilterChainProxy.doFilter(FilterChainProxy.java:176)
org.springframework.web.filter.DelegatingFilterProxy.invokeDelegate(DelegatingFilterProxy.java:344)
org.springframework.web.filter.DelegatingFilterProxy.doFilter(DelegatingFilterProxy.java:261)
编辑:
我如何使用CustomLoginSucessHandler
@Configuration
@EnableWebSecurity
@Import({ DatabaseConfiguration.class })
public class SecurityConfiguration extends WebSecurityConfigurerAdapter {
@Override
protected void configure(HttpSecurity http) throws Exception {
http.authorizeRequests().anyRequest().authenticated().and().formLogin().loginPage("/login.html")
.loginProcessingUrl("/login").permitAll().and().logout().logoutSuccessUrl("/")
.logoutRequestMatcher(new AntPathRequestMatcher("/logout")).permitAll().and().exceptionHandling()
.accessDeniedPage("/403.html");
http.csrf().requireCsrfProtectionMatcher(new CsrfRequestMatcher());
http.formLogin().successHandler(new CustomLoginSucessHandler());
}
...
答案 0 :(得分:0)
要将您的bean放在控制器的其他上下文中,您应该使用下一个注释:
<!--AUTOWIRED // THIS MAYBE YOU ALREADY HAVE-->
<context:component-scan base-package="com.system.rest.natura.controller" />
<!--ADD THIS ONE-->
<context:annotation-config/>
如果您有一个或多个spring.xml配置存档导入它们。
<import resource="/spring-config.xml" />
并且您的CustomLoginSucessHandler也应该有注释:
@Component
答案 1 :(得分:0)
好的,我在这里得到了解决方案。
首先,我需要创建一个名为AuditingConfiguration.java
这样做:
@Configuration
public class AuditingConfiguration {
@Bean
public CustomLoginSucessHandler customLoginSucessHandler(){
return new CustomLoginSucessHandler();
}
}
之后,在我的内部SecurityConfiguration
我这样做了:
@Configuration
@EnableWebSecurity
@Import({ DatabaseConfiguration.class, AuditingConfiguration.class })
public class SecurityConfiguration extends WebSecurityConfigurerAdapter {
@Autowired
private CustomLoginSucessHandler customLoginSucessHandler;
@Override
protected void configure(HttpSecurity http) throws Exception {
http.authorizeRequests().anyRequest().authenticated().and().formLogin().loginPage("/login.html")
.loginProcessingUrl("/login").permitAll().and().logout().logoutSuccessUrl("/")
.logoutRequestMatcher(new AntPathRequestMatcher("/logout")).permitAll().and().exceptionHandling()
.accessDeniedPage("/403.html");
http.csrf().requireCsrfProtectionMatcher(new CsrfRequestMatcher());
http.formLogin().successHandler(customLoginSucessHandler);
}
现在它有效。