一.发现问题:web
spring-springmvc-mybatis 用的spring-security模块作的权限管理,基于数据库的登陆验证,忽然发现不支持中文名称登陆。spring
二.分析问题数据库
项目设置的编码格式是utf-8,网上查阅相关资料,问题出在编码过滤器上,须要在web.xml中加入编码过滤,而且这个过滤器必须放在security过滤器前面,必须在前面,必须在前面,必须在前面。就是以下这段代码:mybatis
<filter> <filter-name>encodingFilter</filter-name> <filter-class> org.springframework.web.filter.CharacterEncodingFilter </filter-class> <init-param> <param-name>encoding</param-name> <param-value>UTF-8</param-value> </init-param> <init-param> <param-name>forceEncoding</param-name> <param-value>true</param-value> </init-param> </filter> <filter-mapping> <filter-name>encodingFilter</filter-name> <url-pattern>/*</url-pattern> </filter-mapping>
但是,个人项目是用java configuration配置的,这种配置方式好像在网上查不到不少资料,基本上都是基于xml配置的。因而,如今问题定位在如何在基于java configuration如何在security filter前面加入编码过滤器。百度不出来了,因而谷歌。这篇文章给了提示http://www.baeldung.com/spring-security-custom-filter(须要翻),mvc
关键部分摘录以下:app
You can register the filter programmatically overriding the configure method from WebSecurityConfigurerAdapter. For example, it works with the addFilterAfter method on a HttpSecurity instance: @Configuration public class CustomWebSecurityConfigurerAdapter extends WebSecurityConfigurerAdapter { @Override protected void configure(HttpSecurity http) throws Exception { http.addFilterAfter( new CustomFilter(), BasicAuthenticationFilter.class); } }
There are a couple of possible methods: addFilterBefore(filter, class) – adds a filter before the position of the specified filter class addFilterAfter(filter, class) – adds a filter after the position of the specified filter class addFilterAt(filter, class) – adds a filter at the location of the specified filter class addFilter(filter) – adds a filter that must be an instance of or extend one of the filters provided by Spring Security
三.解决问题ide
方案1.若是项目是用的xml配置的,上面分析了,能够直接在xml中加入spring的编码过滤器,网上不少这方面的方案。ui
方案2.若是项目是用java configuration配置的(java类配置),解决方法以下,在SecurityConfig.java中加入。google
CharacterEncodingFilter filter1 = new CharacterEncodingFilter(); filter1.setEncoding("utf-8"); http.addFilterBefore(filter1, ChannelProcessingFilter.class);
上面的是关键部分,如下是完整版
@Configuration @EnableWebMvcSecurity public class SecurityConfig extends WebSecurityConfigurerAdapter { @Autowired private DataSource dataSource; @Override protected void configure(HttpSecurity http) throws Exception { CharacterEncodingFilter filter1 = new CharacterEncodingFilter(); filter1.setEncoding("utf-8"); http.addFilterBefore(filter1, ChannelProcessingFilter.class).formLogin().loginPage("/user/login").and().logout() .logoutSuccessUrl("/").and().authorizeRequests().antMatchers("/user/orders").authenticated() .antMatchers("/user/center").authenticated().antMatchers("/shopingCart/confirmation").authenticated() .anyRequest().permitAll().and().csrf().disable(); } @Override protected void configure(AuthenticationManagerBuilder auth) throws Exception { auth.jdbcAuthentication().dataSource(dataSource) .usersByUsernameQuery("select username,password,true from shop_user WHERE username=?") .authoritiesByUsernameQuery("select username,role from shop_user where username=?"); } }
加入编码过滤器以前的代码以下:
@Configuration @EnableWebMvcSecurity public class SecurityConfig extends WebSecurityConfigurerAdapter { @Autowired private DataSource dataSource; @Override protected void configure(HttpSecurity http) throws Exception { http.formLogin().loginPage("/user/login").and().logout() .logoutSuccessUrl("/").and().authorizeRequests().antMatchers("/user/orders").authenticated() .antMatchers("/user/center").authenticated().antMatchers("/shopingCart/confirmation").authenticated() .anyRequest().permitAll().and().csrf().disable(); } @Override protected void configure(AuthenticationManagerBuilder auth) throws Exception { auth.jdbcAuthentication().dataSource(dataSource) .usersByUsernameQuery("select username,password,true from shop_user WHERE username=?") .authoritiesByUsernameQuery("select username,role from shop_user where username=?"); } }