Spring Boot中实现Get or Create逻辑:学生邮箱校验与新增
实现Spring Boot学生注册的Get or Create逻辑
步骤1:扩展StudentRepository添加邮箱查询方法
在你的StudentRepository中添加根据邮箱查询学生的方法,JPA会自动实现该查询逻辑:
public interface StudentRepository extends JpaRepository<Student, Long> { // 根据邮箱查询学生,返回Optional避免空指针 Optional<Student> findByEmail(String email); }
步骤2:自定义异常处理邮箱重复场景
创建自定义异常类,用于标识邮箱已存在的错误:
public class EmailAlreadyExistsException extends RuntimeException { public EmailAlreadyExistsException(String message) { super(message); } }
步骤3:在StudentService中实现校验与新增逻辑
在addNewStudent方法中,先校验邮箱是否存在,存在则抛出异常;不存在则保存新学生。同时捕获数据库唯一约束异常,处理高并发场景下的重复插入问题:
@Service public class StudentService { private final StudentRepository studentRepository; // 构造注入(Spring推荐的注入方式) public StudentService(StudentRepository studentRepository) { this.studentRepository = studentRepository; } public Student addNewStudent(Student student) { // 检查邮箱是否已存在 Optional<Student> existingStudent = studentRepository.findByEmail(student.getEmail()); if (existingStudent.isPresent()) { throw new EmailAlreadyExistsException("email already exist"); } try { return studentRepository.save(student); } catch (SQLIntegrityConstraintViolationException e) { // 捕获数据库唯一约束异常,转为自定义异常 throw new EmailAlreadyExistsException("email already exist"); } } }
步骤4:在StudentController中处理请求与异常
在控制器方法中调用服务层方法,捕获自定义异常并返回对应的响应:
@RestController @RequestMapping("/api/students") public class StudentController { private final StudentService studentService; public StudentController(StudentService studentService) { this.studentService = studentService; } @PostMapping public ResponseEntity<?> registerNewStudent(@RequestBody Student student) { try { Student savedStudent = studentService.addNewStudent(student); // 注册成功返回学生信息和201(Created)状态码 return new ResponseEntity<>(savedStudent, HttpStatus.CREATED); } catch (EmailAlreadyExistsException e) { // 邮箱已存在返回提示信息和400(Bad Request)状态码 return new ResponseEntity<>(e.getMessage(), HttpStatus.BAD_REQUEST); } } }
关键优化:数据库层面添加邮箱唯一约束
为彻底避免重复邮箱问题,在Student实体的email字段上添加唯一约束,防止高并发场景下绕过服务层校验的情况:
@Entity public class Student { @Id @GeneratedValue(strategy = GenerationType.IDENTITY) private Long id; private String name; // 添加唯一约束,确保数据库中邮箱不重复 @Column(unique = true, nullable = false) private String email; // getter、setter方法 }
内容的提问来源于stack exchange,提问作者Fahd Mannaa
相关产品推荐
相关产品推荐

