我是Spring Security的新手,我试图在我的应用程序中保护REST api。我有应用程序URIS然后我有一个像" / api / v1 /"我的休息时间。
我已使用用户名/密码身份验证保护我的应用程序,并且它工作正常,但现在我想保护我的REST api返回401 Unauthorized如果用户未经过身份验证,但我没有'知道如何将两个身份验证保持在一起。
这是怎么回事?
PS:我正在使用Spring MVC和Spring Security
这是我现在的Spring Security配置:
@Configuration
@EnableWebSecurity
@EnableGlobalMethodSecurity(securedEnabled = true)
class SecurityConfig extends WebSecurityConfigurerAdapter {
@Autowired
private AccountService accountService;
@Bean
public TokenBasedRememberMeServices rememberMeServices() {
return new TokenBasedRememberMeServices("remember-me-key", accountService);
}
@Bean
public PasswordEncoder passwordEncoder() {
return new StandardPasswordEncoder();
}
@Override
protected void configure(AuthenticationManagerBuilder auth) throws Exception {
auth.eraseCredentials(true).userDetailsService(accountService).passwordEncoder(passwordEncoder());
}
@Override
protected void configure(HttpSecurity http) throws Exception {
http.authorizeRequests().antMatchers("/", "/favicon.ico", "/resources/**", "/signup").permitAll().anyRequest()
.authenticated()
.and().formLogin().loginPage("/signin").permitAll().failureUrl("/signin?error=1")
.loginProcessingUrl("/authenticate")
.and().logout().logoutUrl("/logout").permitAll().logoutSuccessUrl("/signin?logout")
.and().rememberMe().rememberMeServices(rememberMeServices()).key("remember-me-key")
.and().csrf();
}
@Bean(name = "authenticationManager")
@Override
public AuthenticationManager authenticationManagerBean() throws Exception {
return super.authenticationManagerBean();
}
}
答案 0 :(得分:1)
所以你想要表格登录和安全休息api吗?
jhipster可以生成这样的项目结构。如果您不想使用jhipster,我会举一些示例代码来实现这个目标(虽然我推荐它很酷)
为了未经授权而返回401,你需要这样的东西:
/**
* Returns a 401 error code (Unauthorized) to the client.
*/
@Component
public class Http401UnauthorizedEntryPoint implements AuthenticationEntryPoint {
private final Logger log = LoggerFactory.getLogger(Http401UnauthorizedEntryPoint.class);
/**
* Always returns a 401 error code to the client.
*/
@Override
public void commence(HttpServletRequest request, HttpServletResponse response, AuthenticationException arg2)
throws IOException,
ServletException {
log.debug("Pre-authenticated entry point called. Rejecting access");
response.sendError(HttpServletResponse.SC_UNAUTHORIZED, "Access Denied");
}
}
然后注入并将其添加到您的SecurityConfig.configure(HttpSecurity http)方法中:
http.authenticationEntryPoint(authenticationEntryPoint)
此外,由于REST请求是ajax请求,因此您还需要ajax入口点:
/**
* Returns a 401 error code (Unauthorized) to the client, when Ajax authentication fails.
*/
@Component
public class AjaxAuthenticationFailureHandler extends SimpleUrlAuthenticationFailureHandler {
@Override
public void onAuthenticationFailure(HttpServletRequest request, HttpServletResponse response,
AuthenticationException exception) throws IOException, ServletException {
response.sendError(HttpServletResponse.SC_UNAUTHORIZED, "Authentication failed");
}
}
/**
* Spring Security success handler, specialized for Ajax requests.
*/
@Component
public class AjaxAuthenticationSuccessHandler extends SimpleUrlAuthenticationSuccessHandler {
@Override
public void onAuthenticationSuccess(HttpServletRequest request, HttpServletResponse response,
Authentication authentication)
throws IOException, ServletException {
response.setStatus(HttpServletResponse.SC_OK);
}
}
/**
* Spring Security logout handler, specialized for Ajax requests.
*/
@Component
public class AjaxLogoutSuccessHandler extends AbstractAuthenticationTargetUrlRequestHandler
implements LogoutSuccessHandler {
@Override
public void onLogoutSuccess(HttpServletRequest request, HttpServletResponse response,
Authentication authentication)
throws IOException, ServletException {
response.setStatus(HttpServletResponse.SC_OK);
}
}
将它们添加到安全配置中:
http.successHandler(ajaxAuthenticationSuccessHandler)
.failureHandler(ajaxAuthenticationFailureHandler)
.logoutSuccessHandler(ajaxLogoutSuccessHandler)
所有功劳归功于惊人的jhipster作者。
答案 1 :(得分:-2)
您可以使用基于表达式的访问控制 http://docs.spring.io/spring-security/site/docs/3.0.x/reference/el-access.html
类似的东西,
<intercept-url pattern=/** access="isFullyAuthenticated()/>