当前位置:网站首页>自定义注解实现验证信息的功能
自定义注解实现验证信息的功能
2022-07-01 13:29:00 【喜欢历史的工科生】
自定义注解实现验证逻辑
- 导包
<!-- hibernate 验证框架 -->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-validation</artifactId>
</dependency>
- 定义BO对象,前端传来的业务对象,对象中的属性需要校验
package com.imooc.boapi;
//import com.imooc.annotationcustom.VlogId;
import com.imooc.annotationcustom.VlogId;
import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;
import lombok.ToString;
@Data
@AllArgsConstructor
@NoArgsConstructor
@ToString
public class VlogBOApi {
private String id;
@VlogId(message = "用户不存在,禁止插入视频")
private String vlogerId;
private String url;
private String cover;
private String title;
private Integer width;
private Integer height;
private Integer likeCounts;
private Integer commentsCounts;
}
- 定义一个校验注解
package com.imooc.annotationcustom;
import javax.validation.Constraint;
import javax.validation.Payload;
import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
@Target({
ElementType.FIELD})
@Retention(RetentionPolicy.RUNTIME)
@Constraint(validatedBy = VlogIdValidator.class) //校验的逻辑处理类
public @interface VlogId {
String message();
/** * 将validator进行分类,不同的类group中会执行不同的validator操作 * * @return validator的分类类型 */
Class<?>[] groups() default {
};
/** * 主要是针对bean,很少使用 * * @return 负载 */
Class<? extends Payload>[] payload() default {
};
}
- 同时需要一个校验类,实现一个注解检验的逻辑
package com.imooc.annotationcustom;
import com.imooc.mapper.UsersMapper;
import com.imooc.pojo.Users;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;
import javax.validation.ConstraintValidator;
import javax.validation.ConstraintValidatorContext;
@Slf4j
@Component
public class VlogIdValidator implements ConstraintValidator<VlogId, String> {
@Autowired
UsersMapper usersMapper;
@Override
public void initialize(VlogId constraintAnnotation) {
log.info("注解逻辑初始化");
}
@Override
public boolean isValid(String s, ConstraintValidatorContext constraintValidatorContext) {
Users user = new Users();
user.setId(s);
Users reslut = usersMapper.selectByPrimaryKey(user);
System.out.println("注解拦截生效+package com.imooc.annotationcustom;");
if (reslut == null) {
return false;
} else {
return true;
}
}
}
- 业务代码
@PostMapping("publish")
public GraceJSONResult publish(@Valid @RequestBody VlogBOApi vlogBO) {
// vlogService.createVlog(vlogBO);
return GraceJSONResult.ok();
}
- 校验失败异常,定义一个全局异常捕获,将这个错误返回给前端
@ExceptionHandler(MethodArgumentNotValidException.class)
@ResponseBody
public GraceJSONResult returnMethodArgumentNotValid(MethodArgumentNotValidException e) {
BindingResult result = e.getBindingResult();
Map<String, String> map = getErrors(result);
return GraceJSONResult.errorMap(map);
}
自定义注解来简化开发
目的:做一个点赞次数拦截的功能。过程:需要拦截以后自行确定多少时间内的点赞次数
- 定义注解:
package com.imooc.annotationcustom;
import java.lang.annotation.*;
@Inherited
@Documented
@Target({
ElementType.FIELD, ElementType.TYPE, ElementType.METHOD})
@Retention(RetentionPolicy.RUNTIME)
public @interface RequestLimit {
/** * 时间内 秒为单位 * @return */
int second() default 10;
/*** * 允许访问次数 * @return */
int maxCount() default 5;
}
- 拦截器代码,这里需要获取接口上的自定义注解handlerMethod.getMethodAnnotation
if (handler instanceof HandlerMethod) {
HandlerMethod handlerMethod = (HandlerMethod) handler;
//获取RequestLimit注解
RequestLimit requestLimit = handlerMethod.getMethodAnnotation(RequestLimit.class);
if (null == requestLimit) {
System.out.println("没有获取到注解");
return true; //每加注解说明没有限制,多少次都ok
}
//限制的时间范围
int seconds = requestLimit.second();
//限制时间内的最大次数
int maxCount = requestLimit.maxCount();
//获取用户ip
String userIp = IPUtil.getRequestIp(request);
//判断redis中是否有ip
boolean keyIsExist = redis.keyIsExist(LIKE_VLOG_OPERATE_COUNT + ":" + userIp);
//如果没有这个键,说明当前用户在20s内没有点过赞,因为这个拦截器就是拦截点赞的后端接口,所以如果没有这个键就设置一个键
if (keyIsExist == false) {
redis.set(LIKE_VLOG_OPERATE_COUNT + ":" + userIp, "0", seconds);
System.out.println("ok");
return true;
}
// 返回true,就要判断这个键对应的值的个数
String res = redis.get(LIKE_VLOG_OPERATE_COUNT + ":" + userIp);
if (Integer.valueOf(res) >= maxCount) {
GraceException.display(ResponseStatusEnum.LIKE_VLOG_WAIT_ERROR);
return false;
}
}
return true;
}
- 业务代码
@PostMapping("like")
//TODO: 这里需要调试
@RequestLimit(maxCount = 3, second = 60)
public GraceJSONResult like(@RequestParam String userId,
@RequestParam String vlogerId,
@RequestParam String vlogId,
HttpServletRequest request) {
vlogService.userLikeVlog(userId, vlogId);
redis.increment(REDIS_VLOGER_BE_LIKED_COUNTS + ":" + vlogerId, 1);
redis.increment(REDIS_VLOG_BE_LIKED_COUNTS + ":" + vlogId, 1);
redis.set(REDIS_USER_LIKE_VLOG + ":" + userId + ":" + vlogId, "1");
//------------------------------------------//
//新增功能,限制点赞次数,
String userIp = IPUtil.getRequestIp(request);
redis.increment(LIKE_VLOG_OPERATE_COUNT + ":" + userIp,1);
//-------------------------------------------//
return GraceJSONResult.ok();
}
边栏推荐
- Uni app realizes advertisement scroll bar
- Etcd 概要 机制 和使用场景
- 清华章毓晋老师新书:2D视觉系统和图像技术(文末送5本)
- 北斗通信模块 北斗gps模块 北斗通信终端DTU
- [Jianzhi offer] 55 - ii balanced binary tree
- Enter the top six! Boyun's sales ranking in China's cloud management software market continues to rise
- Liu Dui (fire line safety) - risk discovery in cloudy environment
- Solution to 0xc000007b error when running the game [easy to understand]
- Sign APK with command line
- 3.4 data query in introduction to database system - select (single table query, connection query, nested query, set query, multi table query)
猜你喜欢
minimum spanning tree
当你真的学会DataBinding后,你会发现“这玩意真香”!
陈宇(Aqua)-安全-&gt;云安全-&gt;多云安全
Google Earth Engine(GEE)——全球人类居住区网格数据 1975-1990-2000-2014 (P2016)
面试题目总结(1) https中间人攻击,ConcurrentHashMap的原理 ,serialVersionUID常量,redis单线程,
Summary of interview questions (1) HTTPS man in the middle attack, the principle of concurrenthashmap, serialVersionUID constant, redis single thread,
Enter the top six! Boyun's sales ranking in China's cloud management software market continues to rise
终端识别技术和管理技术
北斗通信模块 北斗gps模块 北斗通信终端DTU
1553B environment construction
随机推荐
【241. 为运算表达式设计优先级】
Judea pearl, Turing prize winner: 19 causal inference papers worth reading recently
SAP intelligent robot process automation (IRPA) solution sharing
单工,半双工,全双工区别以及TDD和FDD区别
焱融看 | 混合云时代下,如何制定多云策略
IO的几种模型 阻塞,非阻塞,io多路复用,信号驱动和异步io
The 14th five year plan of China's environmental protection industry and the report on the long-term goals for 2035 Ⓖ 2022 ~ 2028
uni-app实现广告滚动条
leetcode 322. Coin Change 零钱兑换(中等)
机器学习总结(一):线性回归、岭回归、Lasso回归
Interpretation of R & D effectiveness measurement framework
二传感器尺寸「建议收藏」
La taille de la pile spécifiée est petite, spécifiée à la sortie 328k
8 popular recommended style layout
Computer network interview knowledge points
Chen Yu (Aqua) - Safety - & gt; Cloud Security - & gt; Multicloud security
内容审计技术
6. Wiper part
Applet - multiple text line breaks in view
[241. Design priority for operation expression]