Spring Boot:自定义注解--annotation

news2024/11/23 11:44:51

目录

  • 自定义注解的定义和作用范围
  • 如何创建自定义注解
    • 创建注解接口
  • 如何使用自定义注解进行数据验证
    • 创建注解处理器
    • 控制器中使用注解
  • 如何为字段添加注解

自定义注解的定义和作用范围

  • 自定义注解可以作用在类、方法、属性、参数、异常、字段或其他注解上。

如何创建自定义注解

创建注解接口

在这里插入图片描述

package hanshuhuan.test.anonotion;

import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;

/**
 * 实体检验自定义注解类,根据我们自定义的注解去检查实体各个字段是否在规定的值内
 * @author shuhu
 *
 */
@Target(ElementType.FIELD)
@Retention(RetentionPolicy.RUNTIME)
public @interface ValidateEntity {
	
	public boolean required() default false;//是否检验null
	
	public boolean requiredLeng() default false;//是否检验长度
	
	public boolean requiredMaxValue() default false;//是否检验最大值
	
	public boolean requiredMinValue() default false;//是否检验最小值
	
	public int maxLength() default -1;//最大长度
	
	public int minLength() default -1;//最小长度
	
	public long maxValue() default -1;//最大值
	
	public long minValue() default -1;//最小值
	
	public String errorRequiredMsg() default "";//值为null时的错误提示信息
	
	public String errorMinLengthMsg() default "";//最小长度不满足时的提示信息
	
	public String errorMaxLengthMsg() default "";//最大长度不满足时的提示信息
	
	public String errorMinValueMsg() default "";//最小值不满足时的提示信息
	
	public String errorMaxValueMsg() default "";//最大值不满足时的提示信息
}

如何使用自定义注解进行数据验证

创建注解处理器

package hanshuhuan.test.util;

import java.lang.reflect.Field;

import hanshuhuan.test.anonotion.ValidateEntity;
import hanshuhuan.test.bean.CodeMsg;

/**
 * 验证实体工具类
 * @author shuhu
 *
 */
public class ValidateEntityUtil {
	
	public static CodeMsg validate(Object object){
		Field[] declaredFields = object.getClass().getDeclaredFields();
		for(Field field : declaredFields){
			ValidateEntity annotation = field.getAnnotation(ValidateEntity.class);
			if(annotation != null){
				if(annotation.required()){
					//表示该字段是必填字段
					field.setAccessible(true);
					try {
						Object o = field.get(object);
						//首先判断是否为空
						if(o == null){
							CodeMsg codeMsg = CodeMsg.VALIDATE_ENTITY_ERROR;
							codeMsg.setMsg(annotation.errorRequiredMsg());
							return codeMsg;
						}
						//到这,说明该变量的值不是null
						//首先判断是不是String类型
						if(o instanceof String){
							//若是字符串类型,则检查其长度
							if(annotation.requiredLeng()){
								if(o.toString().length() < annotation.minLength()){
									CodeMsg codeMsg = CodeMsg.VALIDATE_ENTITY_ERROR;
									codeMsg.setMsg(annotation.errorMinLengthMsg());
									return codeMsg;
								}
								if(o.toString().length() > annotation.maxLength()){
									CodeMsg codeMsg = CodeMsg.VALIDATE_ENTITY_ERROR;
									codeMsg.setMsg(annotation.errorMaxLengthMsg());
									return codeMsg;
								}
							}
						}
						//其次来判断是否为数字
						if(isNumberObject(o)){
							//判断是否规定检查最小值
							if(annotation.requiredMinValue()){
								if(Double.valueOf(o.toString()) < annotation.minValue()){
									CodeMsg codeMsg = CodeMsg.VALIDATE_ENTITY_ERROR;
									codeMsg.setMsg(annotation.errorMinValueMsg());
									return codeMsg;
								}
							}
							//判断是否规定检查最大值
							if(annotation.requiredMaxValue()){
								if(Double.valueOf(o.toString()) > annotation.maxValue()){
									CodeMsg codeMsg = CodeMsg.VALIDATE_ENTITY_ERROR;
									codeMsg.setMsg(annotation.errorMaxValueMsg());
									return codeMsg;
								}
							}
						}
					} catch (IllegalArgumentException e) {
						// TODO Auto-generated catch block
						e.printStackTrace();
					} catch (IllegalAccessException e) {
						// TODO Auto-generated catch block
						e.printStackTrace();
					}
				}
			}
		}
		return CodeMsg.SUCCESS;
	}
	
	/**
	 * 检查对象是否是数字类型
	 * @param object
	 * @return
	 */
	public static boolean isNumberObject(Object object){
		if(object instanceof Integer)return true;
		if(object instanceof Long)return true;
		if(object instanceof Float)return true;
		if(object instanceof Double)return true;
		return false;
	}
}

控制器中使用注解

@RequestMapping(value="/login",method=RequestMethod.POST)
@ResponseBody
public Result<Boolean> login(User user,String cpacha){
	if(user == null){
		return Result.error(CodeMsg.DATA_ERROR);
	}
	//用统一验证实体方法验证是否合法
	CodeMsg validate = ValidateEntityUtil.validate(user);
	if(validate.getCode() != CodeMsg.SUCCESS.getCode()){
		return Result.error(validate);
	}
	//表示实体信息合法,开始验证验证码是否为空
	if(StringUtils.isEmpty(cpacha)){
		return Result.error(CodeMsg.CPACHA_EMPTY);
	}
	log.info("ok"+user);
	return Result.success(true);
}

如何为字段添加注解

  • 自定义注解的定义是通过@注解名的方式实现的。
@ValidateEntity(required=true,requiredLeng=true,minLength=4,maxLength=18,errorRequiredMsg="用户名不能为空!",errorMinLengthMsg="用户名长度需大于4!",errorMaxLengthMsg="用户名长度不能大于18!")
@Column(name="username",nullable=false,length=18)
private String username;//用户名
	
@ValidateEntity(required=true,requiredLeng=true,minLength=4,maxLength=32,errorRequiredMsg="密码不能为空!",errorMinLengthMsg="密码长度需大于4!",errorMaxLengthMsg="密码长度不能大于32!")
@Column(name="password",nullable=false,length=32)
private String password;//密码

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1071769.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

Flask与PyQt结合使用时候,阻塞,界面卡死

一.问题起因 做了个服务端, 使用到了python的PYQT6和Flask, PYQT做的是个简单的设置界面: 但是在点击开始运行, 写入flask run的代码的时候, PYQT界面卡死了 代码如下: # 生产环境模式server make_server(0.0.0.0, ser_port, app)server.serve_forever()app.run() 二.问题产…

力扣第404题 左叶子之和 c++ 递归 与 迭代解法

题目 404. 左叶子之和 简单 给定二叉树的根节点 root &#xff0c;返回所有左叶子之和。 示例 1&#xff1a; 输入: root [3,9,20,null,null,15,7] 输出: 24 解释: 在这个二叉树中&#xff0c;有两个左叶子&#xff0c;分别是 9 和 15&#xff0c;所以返回 24示例 2: 输…

【最新技术:grokking】机器学习模型是记忆还是泛化?

Do Machine Learning Models Memorize or Generalize? (pair.withgoogle.com) 机器学习模型是记忆还是泛化&#xff1f; 作者&#xff1a;Adam Pearce、 Asma Ghandeharioun、 Nada Hussein、 Nithum Thain、 Martin Wattenberg 和 Lucas Dixon 2023 年 <> 月 202…

NLP - 数据预处理 - 文本按句子进行切分

NLP - 数据预处理 - 文本按句子进行切分 文章目录 NLP - 数据预处理 - 文本按句子进行切分一、前言二、环境配置1、安装nltk库2、下载punkt分句器 三、运行程序四、额外补充 一、前言 在学习对数据训练的预处理的时候遇到了一个问题&#xff0c;就是如何将文本按句子切分&#…

最新AI智能创作系统源码AI绘画系统/支持GPT联网提问/支持Prompt应用

AI绘图专业设计 不得将程序用作任何违法违纪内容&#xff0c;不要让亲人两行泪 界面部分图解构&#xff1a; 前台show&#xff1a; 前端部署&#xff1a; 安装pm2管理器 点击设置 选择v16.19.1版本-切换版本 再新建一个网站 点击设置 添加反向代理-代理名称随便…

SpringMvc:为什么不能把controller类放到spring容器而必须放到SpringMvc容器?

因为在扫描Handler方法时&#xff0c;只会在SpringMvc容器中去查找bean 定义&#xff0c;不会查找父容器 因此&#xff0c;如果把controller放到Spring容器中直接报404。 而doGetBean方法是会查找子容器的&#xff0c;所以controller中可以注入父容器中的service和dao

设计模式 - 创建型模式考点篇:工厂模式、建造者模式

目录 一、创建型模式 一句话概括 1.1、工厂模式 1.1.1、简单工厂模式&#xff08;非 23 种经典设计模式&#xff09; 概述 案例 1.1.2、静态工厂&#xff08;扩展&#xff09; 1.1.3、工厂方法模式 概念 案例 1.2、建造者模式 1.2.1、概念 1.2.2、案例 1.2.3、建…

Deep learning of free boundary and Stefan problems论文阅读复现

Deep learning of free boundary and Stefan problems论文阅读复现 摘要1. 一维一相Stefan问题1.1 Direct Stefan problem1.2 Inverse Type I1.3 Inverse Type II 2. 一维二相Stefan问题2.1 Direct Stefan problem2.2 Inverse Type I2.3 Inverse Type II 3. 二维一相Stefan问题…

《视觉 SLAM 十四讲》第 7 讲 视觉里程计1 【如何根据图像 估计 相机运动】【特征点法】

github源码链接V2 文章目录 第 7 讲 视觉里程计17.1 特征点法7.1.1 特征点7.1.2 ORB 特征FAST 关键点 ⟹ \Longrightarrow ⟹ Oriented FASTBRIEF 描述子 7.1.3 特征匹配 7.2 实践 【Code】本讲 CMakeLists.txt 7.2.1 使用 OpenCV 进行 ORB 的特征匹配 【Code】7.2.2 手写 O…

windows 2003、2008远程直接关闭远程后设置自动注销会话

1、2003系统&#xff1a; 按开始—运行—输入“tscc.msc”&#xff0c;打开“终端服务配置”。 单击左边窗口的“连接”项&#xff0c;右边窗口中右击“RDP-TCP”&#xff0c;选择“属性”。 单击“会话”项&#xff0c;勾选“替代用户设置”&#xff0c;在“结束已断开的会话”…

C语言中文网 - Shell脚本 - 2

第1章 Shell基础&#xff08;开胃菜&#xff09; 2. Shell是运维人员必须掌握的技能 Linux 运维人员就是负责 Linux 服务器的运行和维护。随着互联网的爆发&#xff0c;Linux 运维在最近几年也迎来了春天&#xff0c;出现了大量的职位需求&#xff0c;催生了一批 Linux 运维培…

远程实时监控管理:5G物联网技术助力配电站管理

配电站远程监控管理系统是基于物联网和大数据处理等技术的一种创新解决方案。该系统通过实时监测和巡检配电场所设备的状态、环境情况、安防情况以及火灾消防等信息&#xff0c;实现对配电站的在线实时监控与现场设备数据采集。 配电站远程监控管理系统通过回传数据进行数据系…

Logback日志框架使用详解以及如何Springboot快速集成

Logback简介 日志系统是用于记录程序的运行过程中产生的运行信息、异常信息等&#xff0c;一般有8个级别&#xff0c;从低到高为All < Trace < Debug < Info < Warn < Error < Fatal < OFF off 最高等级&#xff0c;用于关闭所有日志记录fatal 指出每个…

LSM-Tree笔记

假设Level 0为内存中的Buffer&#xff0c;容量为 B B B&#xff0c;层与层之间的条目数量差 T T T 倍 Tiered Level 1共有 T T T 个runs&#xff0c;每个run的容量均为 B B BLevel 2共有 T T T 个runs&#xff0c;每个run的容量均为 T ⋅ B T\cdot B T⋅BLevel n共有 …

周记学习总结

10.3 今天加载出来了一下歌词&#xff0c;并且画了一下旁边的简单动画&#xff0c;然后画了一下下面的评论&#xff0c;今天主要是看了好多歌词滚动并且让它居中的&#xff0c;一直用的是scrollIntoView这个函数&#xff0c;但是这个函数似乎一直没有用&#xff0c;今天了解了…

多自由度工业机械臂机电系统

经过数百万年的进化创造了最通用和完善的工具——人类手臂。我们现代世界中的一切都得益于这个工具。即使到今天&#xff0c;工业界也没有找到比机器人手臂更多功能的工具来在三维空间中操纵物体&#xff0c;机器人手臂本质上是人类手臂的机电复制品。机器人手臂的多功能性确实…

企业关于低代码的需求——PDM 元数据电子审批流

企业关于低代码的需求 PDM 元数据电子审批流 审批流业务场景是现代企业运营中不可或缺的一环。业务流程从某个特定点开始,然后经过一系列的审批节点,完成流程的审批。这些节点通常由不同级别的人员担任,例如主管、经理、财务、法务和总经理等,每个人都扮演着特定的角色和…

阿里云数据库MongoDB恢复到本地

共两种方式&#xff0c;建议使用第二种的逻辑恢复&#xff0c;比较方便快捷 一、下载物理备份文件 下载的格式是xb的&#xff0c;主要跟实例创建时间有关&#xff0c;2019年03月26日之前创建的实例&#xff0c;物理备份文件格式为tar&#xff0c;后面全部都是xb的格式了&#…

DownloadingImages 下载缓存图片,显示图片文字列表

1. 用到的技术点: 1) Codable : 可编/解码 JSON 数据 2) background threads : 后台线程 3) weak self : 弱引用 4) Combine : 取消器/组合操作 5) Publishers and Subscribers : 发布者与订阅者 6) FileManager : 文件管理器 7) NSCache : 缓存 2. 网址: 2.1 测试接口网址: …

docker入门加实战—docker安装并配置阿里云加速

docker入门加实战—docker安装并配置阿里云加速 为什么要学习docker 在开发和部署项目的过程中&#xff0c;经常会遇到如下问题&#xff1a; 软件安装包名字复杂&#xff0c;不知道去哪里找安装软件和部署项目步骤复杂&#xff0c;容易出错 这就是我们今天要学习Docker技术…