用spring boot建的项目。
现在想自定义一个filter,要求实现用户名,密码,公司id一起验证。
下面是我的代码,参考UsernamePasswordAuthenticationFilter写的。
//这个是filter
public class UsernamePasswordSubdomainAuthenticationFilter extends AbstractAuthenticationProcessingFilter {
protected UsernamePasswordSubdomainAuthenticationFilter() {
super("/login");
}
@Override
public Authentication attemptAuthentication(HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse) throws AuthenticationException, IOException, ServletException {
String username = this.obtainUsername(httpServletRequest);
String password = this.obtainPassword(httpServletRequest);
String subdomain = this.obtainSubDomain(httpServletRequest);
if(username == null) {
username = "";
}
if(password == null) {
password = "";
}
if(subdomain == null){
subdomain = "";
}
username = username.trim();
UsernamePasswordSubdomainAuthenticationToken authRequest = new UsernamePasswordSubdomainAuthenticationToken(username, password, subdomain);
this.setDetails(httpServletRequest, authRequest);
return this.getAuthenticationManager().authenticate(authRequest);
}
protected void setDetails(HttpServletRequest request, UsernamePasswordSubdomainAuthenticationToken authRequest) {
authRequest.setDetails(this.authenticationDetailsSource.buildDetails(request));
}
public String obtainUsername(HttpServletRequest request) {
return request.getParameter("username");
}
public String obtainPassword(HttpServletRequest request) {
return request.getParameter("password");
}
public String obtainSubDomain(HttpServletRequest request) throws MalformedURLException {
URL url = new URL(request.getRequestURL().toString());
String subDomain = url.getHost().split("\\.")[0];
return subDomain;
}
}
//这个是配置
@Configuration
@EnableWebSecurity
public class SecurityConfig extends WebSecurityConfigurerAdapter {
// @Autowired
// private UsernamePasswordSubdomainAuthenticationFilter usernamePasswordSubdomainAuthenticationFilter;
@Bean
public UsernamePasswordSubdomainAuthenticationFilter usernamePasswordSubdomainAuthenticationFilter() {
System.out.println(this.authenticationManager);
UsernamePasswordSubdomainAuthenticationFilter filer = new UsernamePasswordSubdomainAuthenticationFilter();
filer.setAuthenticationManager(authenticationManager);
return filer;
}
// @Autowired
private AuthenticationManager authenticationManager;
@Autowired
public void configureGlobal(AuthenticationManagerBuilder auth) throws Exception {
auth
.inMemoryAuthentication()
.withUser("user") // #1
.password("pass")
.roles("USER")
.and()
.withUser("admin") // #2
.password("password")
.roles("ADMIN","USER");
}
@Override
public void configure(WebSecurity web) throws Exception {
// web
// .ignoring()
// .antMatchers("/resources/**"); // #3
}
@Override
protected void configure(HttpSecurity http) throws Exception {
http
.addFilter(usernamePasswordSubdomainAuthenticationFilter())
.formLogin().disable()
.httpBasic().disable()
.csrf()
.disable();
}
}
然后报了下面的错误
Caused by: java.lang.IllegalArgumentException: authenticationManager must be specified
at org.springframework.util.Assert.notNull(Assert.java:112)
at org.springframework.security.web.authentication.AbstractAuthenticationProcessingFilter.afterPropertiesSet(AbstractAuthenticationProcessingFilter.java:164)
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.invokeInitMethods(AbstractAutowireCapableBeanFactory.java:1633)
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.initializeBean(AbstractAutowireCapableBeanFactory.java:1570)
阿神2017-04-17 15:33:30
因為你沒有為filter注入authenticationManager,authenticationManager可以從authentication-provider取得。
黄舟2017-04-17 15:33:30
私以為 如果你要用springSecurity 但是連整個驗證流程 源碼都沒有摸透最好不要上 不然項目會一敗塗地
多看下源碼就明白了 你的問題報錯已經說明白了 沒有定義authenticationManager 。推薦一篇文章好好看看
http://www.liaozhida.net/springsecurity/springsecurity-%E7%AE%80%E5%8D%95%E6%8B%A6%E6%88%AA% E9%AA%8C%E8%AF%81uml%E5%9B%BE.html
SPRINGSECURITY 原始碼剖析–使用者登入過程發生了什麼事
黄舟2017-04-17 15:33:30
請問你只是去掉了