@Intercepts({
@Signature(type = StatementHandler.class, method = "prepare", args = {Connection.class, Integer.class})
})
@Component
public class SoftDeleteInterceptor implements Interceptor {
@Override
public Object intercept(Invocation invocation) throws Throwable {
StatementHandler handler = (StatementHandler) invocation.getTarget();
BoundSql boundSql = handler.getBoundSql();
String originalSql = boundSql.getSql();
// Append soft delete condition to all SELECT queries
String modifiedSql = originalSql.replace("WHERE 1=1", "WHERE 1=1 AND is_deleted = 0");
// Update the SQL statement through reflection
Field sqlField = boundSql.getClass().getDeclaredField("sql");
sqlField.setAccessible(true);
sqlField.set(boundSql, modifiedSql);
return invocation.proceed();
}
}
Register the interceptor in Spring configuration:
@Configuration
public class WebMvcConfig implements WebMvcConfigurer {
@Autowired
private SoftDeleteInterceptor softDeleteInterceptor;
@Autowired
private AuthenticationInterceptor authInterceptor;
@Override
public void addInterceptors(InterceptorRegistry registry) {
registry.addInterceptor(softDeleteInterceptor);
registry.addInterceptor(authInterceptor)
.excludePathPatterns("/auth/login", "/auth/register");
}
}
For implmeenting soft delete functionality:
- Use
@DeleteMappingin controlelrs - Employ
<update>statements in maper XML files
User availability validation example:
public boolean checkUsernameAvailability(String username) {
User existingUser = userRepository.findByUsername(username);
return existingUser == null || existingUser.isDeleted();
}
public User createUser(User newUser) {
if (checkUsernameAvailability(newUser.getUsername())) {
return userRepository.save(newUser);
} else {
throw new UsernameConflictException("Username already taken");
}
}