DIY自定义ORM框架

ORM框架简介

ORM(Object-Relational Mapping)是一种可以将对象模型(比如实体类)映射到关系模型(比如数据库表)的技术

注:本文只实现了save方法

常见的ORM框架

Hibernate、MyBatis、Spring Data JPA、Mybatis-Plus

框架设计原理

  1. 连接和关闭数据库;
  2. 对象与数据库表的映射;
  3. 数据库的查询和更新;
  4. 数据库结果集与对象之间的映射

实现

添加依赖

xml 复制代码
<dependencies>
    <dependency>
        <groupId>mysql</groupId>
        <artifactId>mysql-connector-java</artifactId>
        <version>8.0.25</version>
    </dependency>
</dependencies>

定义注解

@Table

java 复制代码
@Retention(RetentionPolicy.RUNTIME)
@Target(ElementType.TYPE)
public @interface Table {
    //关联表名
    String name();
}

@Column

java 复制代码
@Retention(RetentionPolicy.RUNTIME)
@Target(ElementType.FIELD)
public @interface Column {
    // 关联列名
    String name();
}

实体类

java 复制代码
@Table(name = "user")//关联自定义注解@Table,将类名与表名建立映射
public class User {
    //关联自定义注解@Column,将属性名与列名建立映射
    @Column(name = "id")
    private int id;

    @Column(name = "username")
    private String username;

    @Column(name = "age")
    private int age;

    public int getId() {
        return id;
    }

    public void setId(int id) {
        this.id = id;
    }

    public String getUsername() {
        return username;
    }

    public void setUsername(String username) {
        this.username = username;
    }

    public int getAge() {
        return age;
    }

    public void setAge(int age) {
        this.age = age;
    }

    @Override
    public String toString() {
        return "User [id=" + id + ", username=" + username + ", age=" + age + "]";
    }   
}

定义ORM框架(核心!!!)

  1. 首先连接数据库
  2. 采用反射获取到注解的内容,也就是通过注解获取到表名和列名
  3. 通过StringBuilder进行sql语句的拼接
  4. 最后执行我们拼接好的sql语句就行
  5. 执行完关闭数据库连接
java 复制代码
package org.example;

import java.sql.Connection;
import java.lang.reflect.Field;
import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.Statement;
public class ORM {
    private Connection conn;

    //构造方法中设置数据库的url、用户名和密码
    public ORM(String url, String user, String password) {
        try {
            //加载Driver驱动
            Class.forName("com.mysql.cj.jdbc.Driver");
            //获取数据库Connection连接对象
            conn = DriverManager.getConnection(url, user, password);
        } catch (Exception e) {
            e.printStackTrace();
        }
    }

    /**
     * 定义一个数据库添加数据的方法
     * @param obj,实体类对象
     */
    public void save(Object obj) {
        Class clazz = obj.getClass();
        //得到某个实体对象上绑定的Table注解
        Table table = (Table) clazz.getAnnotation(Table.class);
        //得到实体类绑定的表名
        String tableName = table.name();

        //拼接insert into插值语句
        StringBuilder sb = new StringBuilder("INSERT INTO ");
        sb.append(tableName).append(" (");

        //获取实体类中每个属性上关联的列名
        Field[] fields = clazz.getDeclaredFields();
        for (Field field : fields) {
            Column column = field.getAnnotation(Column.class);
            if (column != null) {
                //将列名拼接到insert语句中
                sb.append(column.name()).append(",");
            }
        }
        //去掉insert语句中多余的","
        sb.deleteCharAt(sb.length() - 1).append(") VALUES (");

        //在insert语句中,拼接values语句后面的值
        for (Field field : fields) {
            Column column = field.getAnnotation(Column.class);
            if (column != null) {
                //对私有属性设置可访问性
                field.setAccessible(true);
                try {
                    sb.append("'").append(field.get(obj)).append("',");
                } catch (Exception e) {
                    e.printStackTrace();
                }
            }
        }
        //去除insert语句中最后多余的","
        sb.deleteCharAt(sb.length() - 1).append(")");

        try {
            //执行SQL语句
            Statement stmt = conn.createStatement();
            stmt.executeUpdate(sb.toString());
            System.out.println("数据插入成功");
            stmt.close();
        } catch (Exception e) {
            e.printStackTrace();
        }
    }

    /**
     * 关闭数据库连接
     */
    public void close() {
        try {
            conn.close();
        } catch (Exception e) {
            e.printStackTrace();
        }
    }
}

使用我们自定义的ORM框架

java 复制代码
public class Main {
    public static void main(String[] args) {
        ORM orm = new ORM("jdbc:mysql://localhost:3306/activti?useSSL=false", "root", "123456");
        //创建一个用户对象
        User user = new User();
        user.setUsername("aaaaaaa");
        user.setAge(18);
        //调用ORM框架的插入操作
        orm.save(user);
        //关闭数据库连接
        orm.close();
    }
}

截图

数据库设计

执行结果

相关推荐
小信丶18 小时前
Spring Cloud Stream EnableBinding注解详解:定义、应用场景与示例代码
java·spring boot·后端·spring
ffqws_18 小时前
Spring Boot入门:通过简单的注册功能串联Controller,Service,Mapper。(含有数据库建立,连接,及一些关键注解的讲解)
数据库·spring boot·后端
程序边界18 小时前
行标识符机制的技术演进与实践(下)——ROWID与实战应用
后端
Justin3go18 小时前
丢掉沉重的记忆:Codex、Claude Code 与 OpenCode 的上下文压缩术
前端·后端·架构
不懂的浪漫19 小时前
mqtt-plus 架构解析(五):错误处理与 ErrorAction 聚合策略
java·spring boot·后端·物联网·mqtt·架构
卷福同学19 小时前
去掉手机APP开屏广告,李跳跳2.2下载使用
java·后端·算法
程序猿阿越19 小时前
Kafka4源码(三)Share Group共享组
java·后端·源码阅读
Slow菜鸟20 小时前
Spring Cloud 教程(四) | OpenFeign 的作用
后端·spring·spring cloud
GetcharZp20 小时前
告别付费云盘!这款开源 AI 相册神器,颜值与实力双飞,满足你对私人云端的一切幻想!
后端
朦胧之21 小时前
AI 编程工具使用浅谈
前端·后端