Spring Security配置无效:添加依赖及配置后仍返回401错误求助
Spring Security 401未授权问题排查
我是Spring Security新手,在项目中添加Spring Security依赖后立即出现401未授权错误。编写了Security配置类后问题依旧,以下是我的配置类、服务类及控制器类代码,请帮忙排查问题:
配置类代码
package com.hasti.birdy.portfolio.user.config; import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Configuration; import org.springframework.security.config.annotation.web.builders.HttpSecurity; import org.springframework.security.config.annotation.web.configuration.EnableWebSecurity; import org.springframework.security.web.SecurityFilterChain; @Configuration @EnableWebSecurity public class UserConfig { @Bean public SecurityFilterChain filterChain(HttpSecurity httpSecurity) { try { System.out.println("filtering certain requests"); return httpSecurity.csrf() .disable() .authorizeHttpRequests() .requestMatchers("/api/user/**") .permitAll() .and() .httpBasic() .and() .build(); } catch (Exception e) { // TODO Auto-generated catch block e.printStackTrace(); } return null; } @Bean public UserSecurity getUserSecurity() { return new UserSecurity(); } }
服务类代码
package com.hasti.birdy.portfolio.user.service; import java.util.List; import java.util.Set; import java.util.stream.Collectors; import org.springframework.stereotype.Service; import com.hasti.birdy.portfolio.user.config.UserSecurity; import com.hasti.birdy.portfolio.user.dto.PermissionDto; import com.hasti.birdy.portfolio.user.dto.UserDto; import com.hasti.birdy.portfolio.user.mapper.PermissionMapper; import com.hasti.birdy.portfolio.user.mapper.RoleMapper; import com.hasti.birdy.portfolio.user.mapper.UserMapper; import com.hasti.birdy.portfolio.user.model.Permission; import com.hasti.birdy.portfolio.user.model.Role; import com.hasti.birdy.portfolio.user.model.UserModel; import com.hasti.birdy.portfolio.user.repository.RoleRepository; import com.hasti.birdy.portfolio.user.repository.UserRepository; import lombok.RequiredArgsConstructor; import lombok.extern.slf4j.Slf4j; @Service @Slf4j @RequiredArgsConstructor public class UserService { private final UserMapper userMapper; private final RoleMapper roleMapper; private final PermissionMapper permissionMapper; private final UserRepository userRepository; private final RoleRepository roleRepository; private final UserSecurity userSecurity; public String createAdmin(UserDto userDto) { UserModel userModel = userMapper.map(userDto); Role role = roleRepository.findAdminRole(); userModel.setEncryptedPassword(userSecurity.getPasswordEncoder().encode(userDto.getPassword())); userModel.setRole(role); userRepository.save(userModel); return "created"; } public String createCustomer(UserDto userDto) { UserModel userModel = userMapper.map(userDto); Role role = roleRepository.findCustomerRole(); userModel.setEncryptedPassword(userSecurity.getPasswordEncoder().encode(userDto.getPassword())); userModel.setRole(role); userRepository.save(userModel); return "created"; } }
控制器类代码
package com.hasti.birdy.portfolio.user.controller; import org.springframework.http.HttpStatus; import org.springframework.http.HttpStatusCode; import org.springframework.http.ResponseEntity; 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 com.hasti.birdy.portfolio.user.dto.UserDto; import com.hasti.birdy.portfolio.user.service.UserService; import lombok.RequiredArgsConstructor; @RequiredArgsConstructor @RestController @RequestMapping("/api/user") public class UserController { private final UserService userService; @PostMapping("/hsstudio/admin") public ResponseEntity<String> createAdmin(@RequestBody UserDto userDto) { userService.createAdmin(userDto); return ResponseEntity.status(HttpStatus.CREATED).body("created Admin"); } @PostMapping() public ResponseEntity<String> createCustomer(@RequestBody UserDto userDto) { userService.createCustomer(userDto); return ResponseEntity.status(HttpStatus.CREATED).body("created customer "); } }
问题原因及修复方案
核心问题1:SecurityFilterChain构建失败后返回null
你的filterChain方法中,当构建HttpSecurity出现异常时直接返回null,导致Spring Security无法加载自定义过滤规则,转而启用默认安全配置——默认所有请求都需要HTTP Basic认证,因此你配置的/api/user/**放行规则完全不生效,访问时直接返回401。
核心问题2:缺少剩余请求的授权规则兜底
配置中仅定义了/api/user/**的放行规则,但未明确剩余请求的处理逻辑,Spring Security的默认行为可能引发非预期的认证拦截。
修复步骤
修正SecurityFilterChain的构建逻辑
移除try-catch中的返回null逻辑,改为直接抛出异常,确保自定义过滤链能正常加载:@Bean public SecurityFilterChain filterChain(HttpSecurity httpSecurity) throws Exception { System.out.println("filtering certain requests"); return httpSecurity.csrf() .disable() .authorizeHttpRequests(auth -> auth .requestMatchers("/api/user/**").permitAll() .anyRequest().authenticated() // 明确剩余请求需要认证 ) .httpBasic() .and() .build(); }确保PasswordEncoder正确注册为Bean
你的UserSecurity类中使用了密码编码器,但需要确保它被Spring容器管理。可以在UserSecurity中添加:@Bean public PasswordEncoder passwordEncoder() { return new BCryptPasswordEncoder(); }或者直接在
UserConfig中注册该Bean,避免依赖UserSecurity。验证请求路径匹配
控制器中的/api/user和/api/user/hsstudio/admin都能被/api/user/**规则匹配到,这部分无需修改。
内容的提问来源于stack exchange,提问作者Ashish Tripathi
相关产品推荐
相关产品推荐

