嗨,我正在学习Spring安全,我被困在自定义认证过滤器中。我有以下文件:主应用程序文件:SpringAuthApplication.java
package com.example.jwtauth;
import java.util.ArrayList;
import org.springframework.boot.CommandLineRunner;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.context.annotation.Bean;
import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder;
import org.springframework.security.crypto.password.PasswordEncoder;
import com.example.jwtauth.models.Role;
import com.example.jwtauth.models.User;
import com.example.jwtauth.service.UserService;
@SpringBootApplication
public class SpringAuthApplication {
public static void main(String[] args) {
SpringApplication.run(SpringAuthApplication.class, args);
}
@Bean
PasswordEncoder passwordEncoder() {
return new BCryptPasswordEncoder();
}
@Bean
CommandLineRunner run(UserService userService) {
return args -> {
userService.saveRole(new Role(null, "ROLE_USER"));
userService.saveRole(new Role(null, "ROLE_MANAGER"));
userService.saveRole(new Role(null, "ROLE_ADMIN"));
userService.saveRole(new Role(null, "ROLE_SUPER_ADMIN"));
userService.saveUser(new User(null, "Suvodip Mondal", "s.mondal", "1234", new ArrayList<Role>()));
userService.addRoleToUser("s.mondal", "ROLE_SUPER_ADMIN");
userService.saveUser(new User(null, "Akash Arora", "a.arora", "1234", new ArrayList<Role>()));
userService.addRoleToUser("a.arora", "ROLE_ADMIN");
userService.saveUser(new User(null, "Shubham Pathak", "s.pathak", "1234", new ArrayList<Role>()));
userService.addRoleToUser("s.pathak", "ROLE_MANAGER");
userService.saveUser(new User(null, "Karan Sharma", "k.sharma", "1234", new ArrayList<Role>()));
userService.addRoleToUser("k.sharma", "ROLE_USER");
};
}
}
UserController.java
:
package com.example.jwtauth.controllers;
import java.net.URI;
import java.util.List;
import org.springframework.http.ResponseEntity;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import org.springframework.web.servlet.support.ServletUriComponentsBuilder;
import com.example.jwtauth.models.User;
import com.example.jwtauth.service.UserService;
import lombok.Data;
import lombok.RequiredArgsConstructor;
@RestController
@RequestMapping("/api/users")
@RequiredArgsConstructor
public class UserController {
private final UserService userService;
@GetMapping("")
public ResponseEntity<List<User>> getAllUsers() {
return ResponseEntity.ok(userService.listAllUsers());
}
@PostMapping("/create")
public ResponseEntity<User> createUser(@RequestBody User user) {
// ServletUriComponentsBuilder.fromCurrentContextPath() - http://localhost:8080
URI uri= URI.create(ServletUriComponentsBuilder.fromCurrentContextPath().path("/api/user/create").toUriString());
return ResponseEntity.created(uri).body(userService.saveUser(user));
}
@PostMapping("/add-role")
public ResponseEntity<User> createRole(@RequestBody RoleToUserForm form) {
userService.addRoleToUser(form.getUsername(), form.getRoleName());
return ResponseEntity.ok().build();
}
}
@Data
class RoleToUserForm {
private String username;
private String roleName;
}
我的安全配置文件安全配置.java
:
package com.example.jwtauth.security;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.security.authentication.AuthenticationManager;
import org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder;
import org.springframework.security.config.annotation.web.builders.HttpSecurity;
import org.springframework.security.config.annotation.web.configuration.EnableWebSecurity;
import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter;
import org.springframework.security.core.userdetails.UserDetailsService;
import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder;
import com.example.jwtauth.service.filter.CustomAuthenticationFilter;
import org.springframework.security.config.http.SessionCreationPolicy;
import lombok.RequiredArgsConstructor;
@SuppressWarnings("deprecation")
@Configuration @EnableWebSecurity @RequiredArgsConstructor
public class SecurityConfig extends WebSecurityConfigurerAdapter {
private final BCryptPasswordEncoder encoder;
private final UserDetailsService userDetailsService;
@Override
protected void configure(AuthenticationManagerBuilder auth) throws Exception {
auth.userDetailsService(userDetailsService).passwordEncoder(encoder);
}
@Override
protected void configure(HttpSecurity http) throws Exception {
System.out.println("-------------------Configure----------------------------------------");
CustomAuthenticationFilter filter = new CustomAuthenticationFilter(authenticationManager());
// filter.setFilterProcessesUrl("/api/users/create");
http.csrf().disable();
http.sessionManagement().sessionCreationPolicy(SessionCreationPolicy.STATELESS);
http.authorizeRequests().anyRequest().permitAll();
http.addFilter(filter);
}
@Bean
@Override
public AuthenticationManager authenticationManager() throws Exception {
return super.authenticationManagerBean();
}
}
最后我的CustomAuthentication filter文件:< code > customauthenticationfilter . Java :
package com.example.jwtauth.service.filter;
import java.io.IOException;
import java.sql.Date;
import javax.servlet.FilterChain;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import org.springframework.security.authentication.AuthenticationManager;
import org.springframework.security.authentication.UsernamePasswordAuthenticationToken;
import org.springframework.security.core.Authentication;
import org.springframework.security.core.AuthenticationException;
import org.springframework.security.core.userdetails.User;
import org.springframework.security.web.authentication.UsernamePasswordAuthenticationFilter;
import com.auth0.jwt.JWT;
import com.auth0.jwt.algorithms.Algorithm;
import static org.springframework.http.MediaType.APPLICATION_JSON_VALUE;
public class CustomAuthenticationFilter extends UsernamePasswordAuthenticationFilter {
private final AuthenticationManager authenticationManager;
public CustomAuthenticationFilter(AuthenticationManager authenticationManager) {
this.authenticationManager = authenticationManager;
}
@Override
public Authentication attemptAuthentication(HttpServletRequest request, HttpServletResponse response)
throws AuthenticationException {
System.out.println("---------------request------"+request);
String username = request.getParameter("username");
String password = request.getParameter("password");
UsernamePasswordAuthenticationToken token = new UsernamePasswordAuthenticationToken(username, password);
return authenticationManager.authenticate(token);
}
@Override
protected void successfulAuthentication(HttpServletRequest request, HttpServletResponse response, FilterChain chain,
Authentication authResult) throws IOException, ServletException {
User user = (User)authResult.getPrincipal();
System.out.println("---------------user----------"+user);
Algorithm algorithm = Algorithm.HMAC256("secret".getBytes());
String access_token = JWT.create()
.withSubject(user.getUsername())
.withExpiresAt(new Date(System.currentTimeMillis()+10*60*1000))
.withIssuer(request.getRequestURI().toString())
.sign(algorithm);
String refresh_token = JWT.create()
.withSubject(user.getUsername())
.withExpiresAt(new Date(System.currentTimeMillis()+30*60*1000))
.withIssuer(request.getRequestURI().toString())
.sign(algorithm);
System.out.println("---------------access token------------"+access_token);
System.out.println("---------------refresh token------------"+refresh_token);
response.setHeader("access_token", access_token);
response.setHeader("refresh_token", refresh_token);
response.setContentType(APPLICATION_JSON_VALUE);
}
}
因此,我已经将<code>attemptAuthentication</code>方法放在日志中,但似乎请求没有到达那里。此外,我所遵循的教程中,他们使用<code>formurlencoded</code>调用API,但在我的例子中,我得到了<code>HttpMediaTypeNotSupportedException</code>,但<code>application/json</code>在那里工作。但我认为数据类型不是问题,请求至少应该转到attemptAuthentication
方法。我不明白哪里出了问题,我添加了项目github链接作为参考:https://github.com/smondal229/UserAuthService
您是否尝试过添加组件扫描并为定义了过滤器的类添加了包?
如果不尝试添加基本包,也可以尝试过滤器链代理的配置
<bean id="filterChainProxy" class="org.springframework.security.web.FilterChainProxy">
<sec:filter-chain-map path-type="ant">
<sec:filter-chain pattern="/webServices/**" filters="
securityContextPersistenceFilterWithASCFalse,
basicAuthenticationFilter,
exceptionTranslationFilter,
filterSecurityInterceptor" />
<sec:filter-chain pattern="/**" filters="
securityContextPersistenceFilterWithASCTrue,
formLoginFilter,
exceptionTranslationFilter,
filterSecurityInterceptor" />
</sec:filter-chain-map>
</bean>
我实现了一个自定义的身份验证过滤器,效果很好。在设置会话并将身份验证对象添加到安全上下文后,我使用外部身份提供程序并重定向到最初请求的URL。 安全配置 过滤逻辑 目前,我的自定义过滤器(身份确认后)只需硬编码一个角色: 然后将该身份验证对象(上面返回)添加到我的SecurityContext,然后再重定向到所需的endpoint: SecurityContextHolder.getContext
现在我的是的一部分,位于正确的位置。平滑。 但是,由于是,它会被引导拾取并作为筛选器包含。所以我的过滤链看起来真的像: SSOAuthenticationFilter(由于是,因此包含) FilterChainProxy(spring自动配置) ... SecurityContextPersistenceFilter SSOAuthenticationFilter(包含在) ... 显然,我希望在
我的问题是我的SpringConfig类中筛选器的配置。我希望筛选器仅在请求是/authenticate URL时生效,我已将.antmatcher(“/authenticate/**”)添加到筛选器配置中。 当所有其他URL中的该行不再安全时,我可以手动导航到/home,而不进行身份验证,删除该行并对/home进行身份验证。 我应该声明一个只适用于特定URL的筛选器吗? 我如何在维护其他URL的
我在spring MVC项目中实现了一个自定义身份验证提供程序。在我自己的重载authenticate()方法中,我实现了自己的身份验证,其中我构造了自己的UserPasswordAuthenticationToken()并返回对象。 现在,上述对象“UserPasswordAuthentictionToken”中的用户ID被匿名化,密码为null,权限设置为授予该用户的权限。 问题: 这是否会导
我试图在一个反应式Spring Boot应用程序中配置一个Spring Security性,该应用程序具有一个Vuejs前端,在未经身份验证时将用户重定向到外部OpenID提供程序(用于身份验证)。在用户通过OpenID提供程序进行身份验证并重定向回应用程序(前端)后,将根据OpenID提供程序的响应创建用户名密码身份验证令牌(身份验证),并手动进行身份验证。 但是,在执行此操作时,应用程序似乎无
问题内容: 这是我的情况: 一个Web应用程序对许多应用程序执行某种SSO 登录的用户,而不是单击链接,该应用就会向正确的应用发布包含用户信息(名称,pwd [无用],角色)的帖子 我正在其中一个应用程序上实现SpringSecurity以从其功能中受益(会话中的权限,其类提供的方法等) 因此,我需要开发一个 自定义过滤器 -我猜想-能够从请求中检索用户信息,通过自定义 DetailsUserSe