当前位置: 首页 > news >正文

外键约束的应用层维护

1.前言

一般来说 对于不同表格之间的属性约束 我们通常直接使用数据库已经实现好的外键来完成 但是数据库底层实现的外键他的性能很差 这是因为在执行数据库修改操作时 他需要遍历其他所有的表来找出其中可能相关联的属性 一并进行数据库修改(应用层的维护则只需要遍历所有关联外键所在的表) 当然 性能差还有其他很多的原因 这里就提供一个思路 所以要求我们可以通过应用层(业务层)来自行维护一个外键约束

2.实现思路

aop+注解
我们会通过aop去拦截所有形式的数据库修改业务 因为不同形式的数据库修改操作(比如removeById和removeByIds)都有可能影响到其他的约束属性 所以不能够遗漏任何情况 对于任何形式的数据库修改操作而言 都需要对可能存在的约束属性进行检查
同时 也会根据注解来标识外键/主键 同时储存一些相关信息(约束主键所在的表以及属性等等) 注解内部的属性也会提供一些默认值

3.注解实现

1.级联枚举类

所谓级联 其实就是在对某个表格的某条记录执行数据库修改操作时 他的影响会传递给其他所有相关联的记录
有两种策略 一种就是只提醒用户 让用户去做具体决定 另一种就是绕过用户 直接进行当前记录以及相关联的所有记录的数据库修改操作
我们可以设计一个枚举类型来储存有限个的级联策略

/*** 级联策略 所谓级联 其实就是对某条记录的影响会传递给其他相关联的记录* DEFAULT表示默认策略 即提示用户 让用户做具体决定* DELETE表示激进策略 不问用户 直接删除/更新当前记录以及有关联的所有记录*/
public enum ForeignCascade {DEFAULT, DELETE
}

2.ForeignField注解

利用该可选注解我们可以用于标识外键属性/主键属性
在真正应用该注解时 如果主表属性为id 就可以直接全部采取默认值 则不需要为主表属性作用该注解 这就是可选注解的理解

/*** Documented注解在于会将该注解加入到javadoc文档中* Target注解在于设置该注解的作用类型 比如类、方法、属性等等* Retention注解在于设置该注解的作用周期 取值为RUNTIME表示可以作用于编译运行完整的阶段* Repeatable注解作用是该注解可以在同一个地方同时设置多次 并且需要依赖于一个容器储存 本质上 多次使用就相当于在外部封装一层容器*/
@Documented
@Target(ElementType.FIELD)
@Retention(RetentionPolicy.RUNTIME)
@Repeatable(ForeignField.ForeignFields.class)
public @interface ForeignField {// 主表类Class<?> value() default Object.class;// 主表类Class<?> mainTable() default Object.class;// 主表属性名String mainField() default "id";// 对应字段String column() default "";// 级联策略ForeignCascade cascade() default ForeignCascade.DEFAULT;// 容器@Documented@Target(ElementType.FIELD)@Retention(RetentionPolicy.RUNTIME)@interface ForeignFields {ForeignField[] value() default {};}
}

3.ForeignTable注解

利用该可选注解我们可以用于标识外键/主键所在表格

/*** Documented注解的作用在于会将该注解加入到javadoc文档中* Target注解的作用在于该注解只能作用于类上*/
@Documented
@Target(ElementType.TYPE)
@Retention(RetentionPolicy.RUNTIME)
public @interface ForeignTable {// 表名String value() default "";// 表名String name() default "";
}

3.属性信息类/表格信息类实现

1.属性信息类

/*** 该类是属性信息类*/
@Getter
@Setter
public class ForeignFieldInfo {// 当前属性private Field field;// 当前属性对应字段private String column;// 当前属性所在的表格信息类private ForeignTableInfo table;// 引用的属性集合private List<ForeignFieldInfo> mainFields;// 被引用的属性集合private List<ForeignFieldInfo> subFields;// 级联策略private ForeignCascade cascade;// 设置属性 如果属性是私有属性的话 那么就不可以直接由外界访问 这时候 我们应该开放权限public void setField(Field field) {// 表明任意权限的变量都可以访问 即使是private也行field.setAccessible(true);this.field = field;}// 追加引用属性public void addMainField(ForeignFieldInfo mainField) {// 如果集合不存在的话 那么就先创建集合 如果参数已经存在的话 那么就不追加 否则的话 就直接追加if (mainFields == null) {mainFields = new ArrayList<>();} else if (mainFields.contains(mainField)) {return;}mainFields.add(mainField);}// 追加被引用属性public void addSubField(ForeignFieldInfo subField) {// 如果集合不存在的话 先创建集合 如果已经存在 考虑参数是否存在于集合 如果存在 那就不添加 反之则需要添加if (subFields == null) {subFields = new ArrayList<>();} else if (subFields.contains(subField)) {return;}subFields.add(subField);}
}

相关文章:

外键约束的应用层维护

1.前言 一般来说 对于不同表格之间的属性约束 我们通常直接使用数据库已经实现好的外键来完成 但是数据库底层实现的外键他的性能很差 这是因为在执行数据库修改操作时 他需要遍历其他所有的表来找出其中可能相关联的属性 一并进行数据库修改(应用层的维护则只需要遍历所有关联…...

springboot整合log4j2日志框架1

目录 一 log4j基本知识 1.1 log4j的日志级别 1.2 log4j的日志文件结构* 1.2.1 概述 1.2.2 详解 1.3 log4j的日志格式化api 1.3.1 api详解 1.3.2 演示案例 1.3.3 演示案例 1.4 log4j中onmatch和onmismatch的区别* 1.4.1 案例 1.4.2 onmatch的api 1.5 logback&#x…...

06 - Django 视图view

HttpRequest 和 HttpResponse Django中的视图主要用来接受Web请求&#xff0c;并做出响应。 视图的本质就是一个Python中的函数 视图的响应分为两大类 以Json数据形式返回(JsonResponse)以网页的形式返回 重定向到另一个网页 (HttpResponseRedirect)错误视图(4XX,5XX) (Htt…...

基于云计算的资源管理系统

基于云计算的资源管理系统是一种将云计算技术与资源管理技术相结合&#xff0c;以实现资源高效利用和管理的系统。以下是对该系统的详细分析&#xff1a; 一、系统概述 云计算是一种基于网络的计算模式&#xff0c;通过将计算资源和数据存储在云端服务器上&#xff0c;使用户…...

从0入门自主空中机器人-3-【环境与常用软件安装】

关于本课程&#xff1a; 本次课程是一套面向对自主空中机器人感兴趣的学生、爱好者、相关从业人员的免费课程&#xff0c;包含了从硬件组装、机载电脑环境设置、代码部署、实机实验等全套详细流程&#xff0c;带你从0开始&#xff0c;组装属于自己的自主无人机&#xff0c;并让…...

electron node-api addon开发

解决方案入口 拷贝日志以及json等第三方源码 增加包含目录 编写接口 默认模板已经有一个回调函数了 照葫芦画瓢就行 其中几个重要的点要注意 1.参数传入 比如如下的例子&#xff1a; 头文件定义&#xff1a; public:下增加 Napi::Value StartAnswer (const Napi::Callb…...

如何在嵌入式系统或计算机系统中验证boot程序

在嵌入式系统或计算机系统中&#xff0c;验证boot程序&#xff08;引导程序&#xff09;的正确性至关重要&#xff0c;因为它负责初始化系统硬件、加载操作系统内核&#xff0c;并设置系统环境。以下是一些常用的验证boot程序的方法&#xff1a; 一、硬件验证 示波器与逻辑分…...

scala基础学习_运算符

文章目录 scala运算符算术运算符关系运算符逻辑运算符位运算符其他运算符赋值运算符 scala运算符 在 Scala 中&#xff0c;运算符通常被定义为方法。这意味着你可以将运算符视为对象上的方法调用。以下是一些常用的运算符及其对应的操作&#xff1a; 算术运算符 &#xff1a…...

【ANGULAR网站开发】初始环境搭建

1. 初始化angular项目 1.1 创建angular项目 需要安装npm和nodejs&#xff0c;这边不在重新安装 直接安装最新版本的angular npm install -g angular/cli安装指定大版本的angular npm install -g angular/cli181.2 启动angular 使用idea启动 控制台启动 ng serve启动成功…...

【Java】面试题 并发安全 (2)

文章目录 可重入锁&#xff08;ReentrantLock&#xff09;知识总结1. 可重入锁概念与特点2. 基本语法与使用注意事项3. 底层实现原理4. 面试回答要点 synchronized与lock的区别死锁相关面试题讲解死锁产生的四个条件ConcurrentHashMap2. JDK1.7的ConcurrentHashMap结构添加数据…...

springboot启动不了 因一个spring-boot-starter-web底下的tomcat-embed-core依赖丢失

这个包丢失了 启动不了 起因是pom中加入了 <tomcat.version></tomcat.version>版本指定&#xff0c;然后idea自动编译后&#xff0c;包丢了&#xff0c;删除这个配置后再也找不回来&#xff0c; 这个包正常在 <dependency><groupId>org.springframe…...

React 组件的通信方式

在 React 应用开发中&#xff0c;组件之间的通信是构建复杂用户界面和交互逻辑的关键。正确地实现组件通信能够让我们的应用更加灵活和易于维护。以下是几种常见的 React组件通信方式。 一、父子组件通信 1. 通过 props 传递数据&#xff08;父组件向子组件传递数据&#xff0…...

WAV文件双轨PCM格式详细说明及C语言解析示例

WAV文件双轨PCM格式详细说明及C语言解析示例 一、WAV文件双轨PCM格式详细说明1. WAV文件基本结构2. PCM编码方式3. 双轨PCM格式详细说明二、C语言解析WAV文件的代码示例代码说明一、WAV文件双轨PCM格式详细说明 WAV文件是一种用于存储未压缩音频数据的文件格式,广泛应用于音频…...

【ES6复习笔记】数值扩展(16)

介绍 在 JavaScript 中&#xff0c;数值扩展提供了一些额外的功能&#xff0c;使得处理数值变得更加方便。本教程将介绍一些常用的数值扩展方法和属性。 1. Number.EPSILON Number.EPSILON 是 JavaScript 表示的最小精度。它的值接近于 2.2204460492503130808472633361816E-…...

百度热力图数据日期如何选择

目录 1、看日历2、看天气 根据研究内容定&#xff0c;一般如果研究城市活力的话&#xff0c;通常会写“非重大节假日&#xff0c;非重大活动&#xff0c;非极端天气等”。南方晴天不多&#xff0c;有小雨或者中雨都可认为没有影响&#xff0c;要不然在南方很难找到完全一周没有…...

Vue.js 高级组件开发:设计模式与实践

Vue.js 高级组件开发&#xff1a;设计模式与实践 引言一、组合式 API 与动态依赖注入1. 基于 provide/inject 的动态依赖2. 动态依赖注入与懒加载 二、动态渲染与自定义渲染函数1. 使用 Render 函数动态生成内容2. 自定义 vnode 操作 三、复杂场景下的动态表单生成与验证四、高…...

《一文读懂卷积网络CNN:原理、模型与应用全解析》

《一文读懂卷积网络CNN&#xff1a;原理、模型与应用全解析》 一、CNN 基本原理大揭秘&#xff08;一&#xff09;从人类视觉到 CNN 灵感&#xff08;二&#xff09;核心组件详解 二、经典 CNN 模型巡礼&#xff08;一&#xff09;LeNet-5&#xff1a;开山鼻祖&#xff08;二&a…...

MONI后台管理系统-数据敏感字段存储加密

前言&#xff1a;     在我们数据库中&#xff0c;存在很多的敏感数据&#xff0c;如用户表中&#xff0c;存在用户电话、身份证号、邮箱等属于用户的敏感信息&#xff0c;我们通常在存入数据库后&#xff0c;将其进行加密存储&#xff0c;以此来保证数据安全性。     …...

熟悉各类游戏设计模式的用途与限制,如 factory、strategy、mvc、object pool 等

良好的系统分析与设计能力要求开发者熟悉并正确运用各种设计模式来解决特定问题。设计模式是一种针对特定问题的通用解决方案&#xff0c;可提高代码的可复用性、可维护性和可扩展性。以下是对一些常见游戏设计模式的详细分析&#xff0c;包括其用途、限制和代码示例。 一、工厂…...

【RabbitMQ高级篇】消息可靠性问题(1)

目录 1.消息可靠性 1.1.生产者消息确认 1.1.1.修改配置 1.1.2.定义Return回调 1.1.3.定义ConfirmCallback 1.2.消息持久化 1.2.1.交换机持久化 1.2.2.队列持久化 1.2.3.消息持久化 1.3.消费者消息确认 1.3.1.演示none模式 1.3.2.演示auto模式 1.4.消费失败重试机制…...

Python|GIF 解析与构建(5):手搓截屏和帧率控制

目录 Python&#xff5c;GIF 解析与构建&#xff08;5&#xff09;&#xff1a;手搓截屏和帧率控制 一、引言 二、技术实现&#xff1a;手搓截屏模块 2.1 核心原理 2.2 代码解析&#xff1a;ScreenshotData类 2.2.1 截图函数&#xff1a;capture_screen 三、技术实现&…...

生成xcframework

打包 XCFramework 的方法 XCFramework 是苹果推出的一种多平台二进制分发格式&#xff0c;可以包含多个架构和平台的代码。打包 XCFramework 通常用于分发库或框架。 使用 Xcode 命令行工具打包 通过 xcodebuild 命令可以打包 XCFramework。确保项目已经配置好需要支持的平台…...

Android Wi-Fi 连接失败日志分析

1. Android wifi 关键日志总结 (1) Wi-Fi 断开 (CTRL-EVENT-DISCONNECTED reason3) 日志相关部分&#xff1a; 06-05 10:48:40.987 943 943 I wpa_supplicant: wlan0: CTRL-EVENT-DISCONNECTED bssid44:9b:c1:57:a8:90 reason3 locally_generated1解析&#xff1a; CTR…...

SpringBoot+uniapp 的 Champion 俱乐部微信小程序设计与实现,论文初版实现

摘要 本论文旨在设计并实现基于 SpringBoot 和 uniapp 的 Champion 俱乐部微信小程序&#xff0c;以满足俱乐部线上活动推广、会员管理、社交互动等需求。通过 SpringBoot 搭建后端服务&#xff0c;提供稳定高效的数据处理与业务逻辑支持&#xff1b;利用 uniapp 实现跨平台前…...

Neo4j 集群管理:原理、技术与最佳实践深度解析

Neo4j 的集群技术是其企业级高可用性、可扩展性和容错能力的核心。通过深入分析官方文档,本文将系统阐述其集群管理的核心原理、关键技术、实用技巧和行业最佳实践。 Neo4j 的 Causal Clustering 架构提供了一个强大而灵活的基石,用于构建高可用、可扩展且一致的图数据库服务…...

前端开发面试题总结-JavaScript篇(一)

文章目录 JavaScript高频问答一、作用域与闭包1.什么是闭包&#xff08;Closure&#xff09;&#xff1f;闭包有什么应用场景和潜在问题&#xff1f;2.解释 JavaScript 的作用域链&#xff08;Scope Chain&#xff09; 二、原型与继承3.原型链是什么&#xff1f;如何实现继承&a…...

Spring AI与Spring Modulith核心技术解析

Spring AI核心架构解析 Spring AI&#xff08;https://spring.io/projects/spring-ai&#xff09;作为Spring生态中的AI集成框架&#xff0c;其核心设计理念是通过模块化架构降低AI应用的开发复杂度。与Python生态中的LangChain/LlamaIndex等工具类似&#xff0c;但特别为多语…...

蓝桥杯3498 01串的熵

问题描述 对于一个长度为 23333333的 01 串, 如果其信息熵为 11625907.5798&#xff0c; 且 0 出现次数比 1 少, 那么这个 01 串中 0 出现了多少次? #include<iostream> #include<cmath> using namespace std;int n 23333333;int main() {//枚举 0 出现的次数//因…...

Mysql中select查询语句的执行过程

目录 1、介绍 1.1、组件介绍 1.2、Sql执行顺序 2、执行流程 2.1. 连接与认证 2.2. 查询缓存 2.3. 语法解析&#xff08;Parser&#xff09; 2.4、执行sql 1. 预处理&#xff08;Preprocessor&#xff09; 2. 查询优化器&#xff08;Optimizer&#xff09; 3. 执行器…...

【Android】Android 开发 ADB 常用指令

查看当前连接的设备 adb devices 连接设备 adb connect 设备IP 断开已连接的设备 adb disconnect 设备IP 安装应用 adb install 安装包的路径 卸载应用 adb uninstall 应用包名 查看已安装的应用包名 adb shell pm list packages 查看已安装的第三方应用包名 adb shell pm list…...