自定义轻量级ORM,MxDaoManager
前段时间看到了ORM,了解到 ORM是对象关系映射(英语:(Object Relational Mapping,简称ORM,或O/RM,或O/R mapping),是一种程序技术,用于实现面向对象编程语言里不同类型系统的数据之间的转换 [1] 。从效果上说,它其实是创建了一个可在编程语言里使用的--“虚拟对象数据库”。简单点说就是 讲对象的操作装换为sql语句去执行,然后我为了让自己更加升入的了解他的原理,就自己模拟写了一个简单的ORM(MXDaoManager),大神们请多多建议,主要是利用了泛型和java反射的原理来实现的,
1.项目结构
MxDaoData这个就是基类,直接继承这个类就可以去调用insert,delete,update,
我这里提供了6个方法,分别是
1.updataAll(String keycolumn) 更新所有属性的值,keycolumn 是主键的属性名,楼主这里偷懒了,没有用@interface去表明主键,想的是灵活性得更好一点才行,所以就自行输入了,绝对不是头狼
2.updata(String columns, String keycolumn) 更新指定属性名的值,columns可以用,来表示多个列表,keycolumn也是一样的
3.insert(String columns) 指定插入属性名,可以用",“来分割多个属性名称
4.insertNoColumns(String columns) 不插入指定属性名的值,同样可以用”,"来分割多个属性名称
5.insert() 插入所有的属性名的值
6.delete(String column) 删除字段为column = 变量column对应的值的数据
来看下源码:
package com.mx.mxdao;
import java.lang.reflect.Field;
public class MxDaoData {
/**
* 更细所有参数
*
* @return 是否成功
* @throws Exception
*/
public boolean updataAll(String keycolumn) throws Exception {
Class<? extends MxDaoData> ins = this.getClass();
Field[] fileds = ins.getDeclaredFields();
int size = fileds.length;// 属性个数
StringBuffer sqlstr = new StringBuffer();
sqlstr.append("update " + ins.getSimpleName() + " set ");
Object[] args = new Object[size + 1];
for (int i = 0; i < fileds.length; i++) {
Field f = fileds[i];
f.setAccessible(true); // 设置些属性是可以访问的
String key = f.getName();// key:得到属性名
args[i] = f.get(this);
sqlstr.append(key + "=?,");
}
sqlstr.deleteCharAt(sqlstr.length() - 1);
Field f = ins.getDeclaredField(keycolumn);
f.setAccessible(true); // 设置些属性是可以访问的
args[size] = f.get(this);
if (args[size] == null) {
return false;
}
sqlstr.append(" where " + keycolumn + " = ? ");
boolean result = MxDaoManager.exceuteSql(sqlstr.toString(), args);
return result;
}
/**
* 更新哪些列
*
* @param columns
* 更新列的名称
* @param keycolumn
* 唯一参数列名称
* @return 是否成功
* @throws Exception
*/
public boolean updata(String columns, String keycolumn) throws Exception {
Class<? extends MxDaoData> ins = this.getClass();
String[] columnstr = columns.split(",");
Field[] fileds = new Field[columnstr.length];
for (int j = 0; j < columnstr.length; j++) {
fileds[j] = ins.getDeclaredField(columnstr[j]);
}
int size = fileds.length;// 属性个数
StringBuffer sqlstr = new StringBuffer();
sqlstr.append("update " + ins.getSimpleName() + " set ");
Object[] args = new Object[size + 1];
for (int i = 0; i < fileds.length; i++) {
Field f = fileds[i];
f.setAccessible(true); // 设置些属性是可以访问的
String key = f.getName();// key:得到属性名
sqlstr.append(key + "=? ");
args[i] = f.get(this);
}
Field f = ins.getDeclaredField(keycolumn);
f.setAccessible(true); // 设置些属性是可以访问的
sqlstr.append(" where " + keycolumn + " = ? ");
args[size] = f.get(this);
boolean result = MxDaoManager.exceuteSql(sqlstr.toString(), args);
return result;
}
/**
* 插入一条记录
*
* @param columns
* 插入值的列名称
* @return 是否成功
* @throws Exception
*/
public boolean insert(String columns) throws Exception {
Class<? extends MxDaoData> ins = this.getClass();
String[] columnstr = columns.split(",");
Field[] fileds = new Field[columnstr.length];
for (int j = 0; j < columnstr.length; j++) {
fileds[j] = ins.getDeclaredField(columnstr[j]);
}
int size = fileds.length;// 属性个数
StringBuffer sqlstr = new StringBuffer();
StringBuffer valuename = new StringBuffer(" values (");
sqlstr.append("insert into " + ins.getSimpleName() + " (");
Object[] args = new Object[size];
for (int i = 0; i < fileds.length; i++) {
Field f = fileds[i];
f.setAccessible(true); // 设置些属性是可以访问的
args[i] = f.get(this);
String key = f.getName();// key:得到属性名
sqlstr.append(key + ",");
valuename.append("?,");
}
sqlstr.deleteCharAt(sqlstr.length() - 1);
sqlstr.append(")");
valuename.deleteCharAt(valuename.length() - 1);
valuename.append(")");
sqlstr.append(valuename);
boolean result = MxDaoManager.exceuteSql(sqlstr.toString(), args);
return result;
}
/**
* 插入一条数据 不插入某些值
*
* @param columns
* 不插入的列名
* @return 是否成功
* @throws Exception
*/
public boolean insertNoColumns(String columns) throws Exception {
Class<? extends MxDaoData> ins = this.getClass();
String[] columnstr = columns.split(",");
Field[] fileds = ins.getDeclaredFields();
int size = fileds.length - columnstr.length;// 属性个数
StringBuffer sqlstr = new StringBuffer();
StringBuffer valuename = new StringBuffer(" values (");
sqlstr.append("insert into " + ins.getSimpleName() + " (");
Object[] args = new Object[size];
for (int i = 0; i < fileds.length; i++) {
Field f = fileds[i];
f.setAccessible(true); // 设置些属性是可以访问的
String key = f.getName();// key:得到属性名
if (columns.indexOf(key) >= 0) {
continue;
}
args[i] = f.get(this);
sqlstr.append(key + ",");
valuename.append("?,");
}
sqlstr.deleteCharAt(sqlstr.length() - 1);
sqlstr.append(")");
valuename.deleteCharAt(valuename.length() - 1);
valuename.append(")");
sqlstr.append(valuename);
boolean result = MxDaoManager.exceuteSql(sqlstr.toString(), args);
return result;
}
/**
* 插入所有的值
*
* @return 是否成功
* @throws Exception
*/
public boolean insert() throws Exception {
Class<? extends MxDaoData> ins = this.getClass();
Field[] fileds = ins.getDeclaredFields();
int size = fileds.length;// 属性个数
StringBuffer sqlstr = new StringBuffer();
StringBuffer valuename = new StringBuffer(" values (");
sqlstr.append("insert into " + ins.getSimpleName() + " (");
Object[] args = new Object[size];
for (int i = 0; i < fileds.length; i++) {
Field f = fileds[i];
f.setAccessible(true); // 设置些属性是可以访问的
args[i] = f.get(this);
String key = f.getName();// key:得到属性名
sqlstr.append(key + ",");
valuename.append("?,");
}
sqlstr.deleteCharAt(sqlstr.length() - 1);
sqlstr.append(")");
valuename.deleteCharAt(valuename.length() - 1);
valuename.append(")");
sqlstr.append(valuename);
boolean result = MxDaoManager.exceuteSql(sqlstr.toString(), args);
return result;
}
/**
* 删除
*
* @param columns
* 更新列的名称
* @param keycolumn
* 唯一参数列名称
* @return
* @throws Exception
*/
public boolean delete(String column) throws Exception {
Class<? extends MxDaoData> ins = this.getClass();
Field filed = ins.getDeclaredField(column);
Object[] args = new Object[1];
filed.setAccessible(true); // 设置些属性是可以访问的
args[0] = filed.get(this);
String sqlstr = "delete from " + ins.getSimpleName() + " where " + column + " = ?";
boolean result = MxDaoManager.exceuteSql(sqlstr, args);
return result;
}
}
MxDaoManager这个就是数据库管理类, 由他来实现与数据库交换数据,上面的那个基类就是将对应的操作转换为sql语句交由MxDaoManager类去处理
MxDbInfo类就是用来管理与sql连接的信息
MxDaoManager:
package com.mx.mxdao;
import java.util.Arrays;
import java.util.List;
public class MxDaoManager {
private static MxDaoManagerUtil instance;
/**
* 查找符合条件的对象
*
* @param ins
* @return
* @throws Exception
*/
public static <T> List<T> find(Class<T> ins) throws Exception {
List<T> list = instance.find(ins);
return list;
}
/**
* select语句
* @param selectvalue select语句 示例 " id,name "
* @return
* @throws ClassNotFoundException
*/
public static MxDaoManagerUtil Select(String selectvalue) throws ClassNotFoundException {
if (instance == null) {
instance = new MxDaoManagerUtil();
}
instance.setSelectvalue(selectvalue);
return instance;
}
/**
* @param where where语句 示例:" id = ? and name = ?"
* @param wherevalue 条件值 示例: "1,2,3"
* @return
* @throws ClassNotFoundException
*/
public static MxDaoManagerUtil Where(String where, String wherevalue) throws ClassNotFoundException {
String[] values = wherevalue.split(",");
List<String> value = Arrays.asList(values);
if (instance == null) {
instance = new MxDaoManagerUtil();
}
instance.setWherevalue(where);
instance.setValue(value);
return instance;
}
/**
* 限制条数语句
* @param limit 限制值 示例: " 6,10 " 类似于 limit 6,10
* @return
* @throws ClassNotFoundException
*/
public static MxDaoManagerUtil limit(String limit) throws ClassNotFoundException {
if (instance == null) {
instance = new MxDaoManagerUtil();
}
instance.setLimitvalue(limit);
return instance;
}
/**
* 排序语句
* @param oderby 排序语句 示例 " id desc" 等同于 orderby id desc
* @return
* @throws ClassNotFoundException
*/
public static MxDaoManagerUtil orderby(String oderby) throws ClassNotFoundException {
if (instance == null) {
instance = new MxDaoManagerUtil();
}
instance.setOrdervalue(oderby);
return instance;
}
/**
* 执行sql语句
*
* @param sql
* @param args
* @return
* @throws Exception
*/
public static boolean exceuteSql(String sql, Object[] args) throws Exception {
boolean result = instance.exceuteSql(sql, args);
return result;
}
/**
* 查找符合条件的对象
*
* @param ins
* @return
* @throws Exception
*/
public static <T> List<T> findByColumn(Class<T> ins, String column, String value) throws Exception {
List<T> list = instance.findByColumn(ins, column, value);
return list;
}
/**
* 按条件更新
*
* @param ins 更新数据 "id=?,usernam=?"
* @param values 数据"1,2,3,4"
* @return
* @throws Exception
*/
public static <T> boolean upDateByWhere(Class<T> ins, String update, String values) throws Exception {
boolean reult = instance.upDateByWhere(ins, update, values);
return reult;
}
/**
* 按条件删除
*
* @param ins
* @return
* @throws Exception
*/
public static <T> boolean deleteByWhere(Class<T> ins, String column, String value) throws Exception {
boolean reult = instance.deleteByWhere(ins, column, value);
return reult;
}
/**
* 查找符合条件的对象
*
* @param ins
* @return
* @throws Exception
*/
public static <T> T findInsByColumn(Class<T> ins, String column, String value) throws Exception {
T s = instance.findInsByColumn(ins, column, value);
return s;
}
}
MxDaoManagerUtil:
package com.mx.mxdao;
import java.lang.reflect.Field;
import java.sql.DriverManager;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
public class MxDaoManagerUtil extends MxDbInfo{
private String selectvalue = "*";
private String wherevalue = "";
private String limitvalue = "";
private String groupvalue = "";
private String ordervalue = "";
private List<String> value = new ArrayList<>();
public String getSelectvalue() {
return selectvalue;
}
public void setSelectvalue(String selectvalue) {
this.selectvalue = selectvalue;
}
public String getWherevalue() {
return wherevalue;
}
public void setWherevalue(String wherevalue) {
this.wherevalue = wherevalue;
}
public String getLimitvalue() {
return limitvalue;
}
public void setLimitvalue(String limitvalue) {
this.limitvalue = limitvalue;
}
public String getGroupvalue() {
return groupvalue;
}
public void setGroupvalue(String groupvalue) {
this.groupvalue = groupvalue;
}
public String getOrdervalue() {
return ordervalue;
}
public void setOrdervalue(String ordervalue) {
this.ordervalue = ordervalue;
}
public List<String> getValue() {
return value;
}
public void setValue(List<String> value) {
this.value = value;
}
public MxDaoManagerUtil() throws ClassNotFoundException {
// TODO Auto-generated constructor stub
Class.forName(driver); // 加载驱动
}
/**
* select语句
* @param selectvalue select语句 示例 " id,name "
* @return
*/
public MxDaoManagerUtil Select(String selectvalue) {
this.setSelectvalue(selectvalue);
return this;
}
/**
* @param where where语句 示例:" id = ? and name = ?"
* @param wherevalue 条件值 示例: "1,2,3"
* @return
*/
public MxDaoManagerUtil Where(String where, String wherevalue) {
String[] values = wherevalue.split(",");
List<String> value = Arrays.asList(values);
this.setWherevalue(where);
this.setValue(value);
return this;
}
/**
* 限制条数语句
* @param limit 限制值 示例: " 6,10 " 类似于 limit 6,10
* @return
*/
public MxDaoManagerUtil limit(String limit) {
this.setLimitvalue(limit);
return this;
}
/**
* 排序语句
* @param oderby 排序语句 示例 " id desc" 等同于 orderby id desc
* @return
*/
public MxDaoManagerUtil orderby(String oderby) {
this.setOrdervalue(oderby);
return this;
}
/**
* 查找符合条件的对象
*
* @param ins
* @return
* @throws Exception
*/
public <T> List<T> find(Class<T> ins) throws Exception {
// 测试代码
// String sql = "select " + selectvalue + " from " + ins.getSimpleName().toLowerCase();
// if (wherevalue.length() != 0) {
// sql += " where " + wherevalue;
// }
// if (limitvalue.length() != 0) {
// sql += " limit " + limitvalue;
// }
// if (ordervalue.length() != 0) {
// sql += " orderby " + ordervalue;
// }
// System.out.println("sql: " + sql);
// JSONArray jsonObject = new JSONArray();
// if (value.size() != 0) {
// for (int j = 0; j < value.size(); j++) {
// jsonObject.put(value.get(j));
// }
// }
// System.out.println("values: " + jsonObject.toString());
// reset();
// return null;
List<T> list = new ArrayList<>();
conn = DriverManager.getConnection(sqlurl, user, password);
PreparedStatement pe = null;
if (!conn.isClosed()) {
String sql = "select " + selectvalue + " from " + ins.getSimpleName().toLowerCase();
if (wherevalue.length() != 0) {
sql += " where " + wherevalue;
}
if (limitvalue.length() != 0) {
sql += " limit " + limitvalue;
}
if (ordervalue.length() != 0) {
sql += " orderby " + ordervalue;
}
pe = conn.prepareStatement(sql);
if (value.size() != 0) {
for (int j = 0; j < value.size(); j++) {
pe.setObject(j + 1, value.get(j));
}
}
ResultSet rSet = pe.executeQuery();
Field[] fileds = null;
if (selectvalue.indexOf("*") >= 0) {
fileds = ins.getFields();
} else {
String[] args = selectvalue.split(",");
fileds = new Field[args.length];
for (int i = 0; i < args.length; i++) {
fileds[i] = ins.getDeclaredField(args[i]);
}
}
while (rSet.next()) {
T s = ins.newInstance();
for (Field field : fileds) {
String type = field.getType().getSimpleName();
if (supportTypeStr.indexOf(type) >= 0) {
// 字符类型
Object value = rSet.getObject(field.getName());
field.set(s, value);
}
}
list.add(s);
}
rSet.close();
}
pe.close();
conn.close();
reset();
return list;
}
/**
* 执行sql语句
*
* @param sql
* @param args
* @return
* @throws Exception
*/
public boolean exceuteSql(String sql, Object[] args) throws Exception {
conn = DriverManager.getConnection(sqlurl, user, password);
PreparedStatement pe = null;
pe = conn.prepareStatement(sql);
for (int i = 0; i < args.length; i++) {
pe.setObject(i + 1, args[i]);
}
int result = pe.executeUpdate();
pe.close();
conn.close();
reset();
return result != 0;
}
/**
* 查找符合条件的对象
*
* @param ins
* @return
* @throws Exception
*/
public <T> List<T> findByColumn(Class<T> ins, String column, String value) throws Exception {
// 测试代码
// String sql = "select " + selectvalue + " from " + ins.getSimpleName().toLowerCase() + " where " + column + "=?";
// System.out.println("sql: " + sql);
// System.out.println("values: " + value);
// reset();
// return null;
List<T> list = new ArrayList<>();
conn = DriverManager.getConnection(sqlurl, user, password);
PreparedStatement pe = null;
if (!conn.isClosed()) {
String sql = "select " + selectvalue + " from " + ins.getSimpleName().toLowerCase() + " where " + column + "=?";
pe = conn.prepareStatement(sql);
pe.setObject(1, value);
ResultSet rSet = pe.executeQuery();
Field[] fileds = null;
if (selectvalue.indexOf("*") >= 0) {
fileds = ins.getFields();
} else {
String[] args = selectvalue.split(",");
fileds = new Field[args.length];
for (int i = 0; i < args.length; i++) {
fileds[i] = ins.getDeclaredField(args[i]);
}
}
while (rSet.next()) {
T s = ins.newInstance();
for (Field field : fileds) {
String type = field.getType().getSimpleName();
if (supportTypeStr.indexOf(type) >= 0) {
// 字符类型
Object values = rSet.getObject(field.getName());
field.set(s, values);
}
}
list.add(s);
}
rSet.close();
}
pe.close();
conn.close();
reset();
return list;
}
/**
* 按条件更新
*
* @param ins 更新数据 "id=?,usernam=?"
* @param values 数据"1,2,3,4"
* @return
* @throws Exception
*/
public <T> boolean upDateByWhere(Class<T> ins, String update, String values) throws Exception {
// 测试代码
// StringBuffer sql = new StringBuffer("update " + ins.getSimpleName().toLowerCase() + " set ");
// String[] updates = update.split(",");
// for(String updatecolumn : updates) {
// sql.append(updatecolumn + "=?,");
// }
// sql.deleteCharAt(sql.length() - 1);
// if (wherevalue.length() != 0) {
// sql.append(" where " + wherevalue);
// }
// System.out.println("sql: " + sql.toString());
//
// String[] valus = values.split(",");
// JSONArray jsonObject = new JSONArray();
// if (valus.length != 0) {
// for (int j = 0; j < valus.length; j++) {
// jsonObject.put(valus[j]);
// }
// }
// for(int j = 0; j < value.size(); j++) {
// jsonObject.put(value.get(j));
// }
// System.out.println("values: " + jsonObject.toString());
// reset();
// return false;
conn = DriverManager.getConnection(sqlurl, user, password);
PreparedStatement pe = null;
int reult = 0;
if (!conn.isClosed()) {
StringBuffer sql = new StringBuffer("update " + ins.getSimpleName().toLowerCase() + " set ");
String[] updates = update.split(",");
for(String updatecolumn : updates) {
sql.append(updatecolumn + "=?,");
}
sql.deleteCharAt(sql.length() - 1);
if (wherevalue.length() != 0) {
sql.append(" where " + wherevalue);
}
String[] valus = values.split(",");
pe = conn.prepareStatement(sql.toString());
int i = 0;
for (i = 0; i < valus.length; i++) {
pe.setObject(i + 1, valus[i]);
}
for(int j = i; j < i + value.size(); j++) {
pe.setObject(j + 1, value.get(j - i));
}
reult = pe.executeUpdate();
}
pe.close();
conn.close();
reset();
return reult != 0;
}
/**
* 按条件删除
*
* @param ins
* @return
* @throws Exception
*/
public <T> boolean deleteByWhere(Class<T> ins, String column, String value) throws Exception {
// 测试代码
// String sql = "delete from " + ins.getSimpleName().toLowerCase() + " where " + column + "=?";
// System.out.println("sql: " + sql);
// System.out.println("values: " + value);
// reset();
// return false;
conn = DriverManager.getConnection(sqlurl, user, password);
PreparedStatement pe = null;
int reult = 0;
if (!conn.isClosed()) {
String sql = "delete " + ins.getSimpleName().toLowerCase() + " where " + column + "=?";
pe = conn.prepareStatement(sql);
pe.setObject(1, value);
reult = pe.executeUpdate();
}
pe.close();
conn.close();
reset();
return reult != 0;
}
/**
* 查找符合条件的对象
*
* @param ins
* @return
* @throws Exception
*/
public <T> T findInsByColumn(Class<T> ins, String column, String value) throws Exception {
// 测试代码
// String sql = "select " + selectvalue + " from " + ins.getSimpleName().toLowerCase() + " where " + column + "=?";
// System.out.println("sql: " + sql);
// System.out.println("values: " + value);
// reset();
// return null;
conn = DriverManager.getConnection(sqlurl, user, password);
PreparedStatement pe = null;
T s = ins.newInstance();
if (!conn.isClosed()) {
String sql = "select " + selectvalue + " from " + ins.getSimpleName().toLowerCase() + " where " + column + "=?";
pe = conn.prepareStatement(sql);
pe.setObject(1, value);
ResultSet rSet = pe.executeQuery();
Field[] fileds = null;
if (selectvalue.indexOf("*") >= 0) {
fileds = ins.getFields();
} else {
String[] args = selectvalue.split(",");
fileds = new Field[args.length];
for (int i = 0; i < args.length; i++) {
fileds[i] = ins.getDeclaredField(args[i]);
}
}
if (rSet.next()) {
for (Field field : fileds) {
String type = field.getType().getSimpleName();
if (supportTypeStr.indexOf(type) >= 0) {
// 字符类型
Object values = rSet.getObject(field.getName());
field.set(s,values);
}
}
}
rSet.close();
}
pe.close();
conn.close();
reset();
return s;
}
/**
* 重置所有参数
*/
private void reset() {
selectvalue = "*";
wherevalue = "";
limitvalue = "";
groupvalue = "";
ordervalue = "";
value = new ArrayList<>();
}
}
啊,不想写了,就是这样,=-=
看下怎么使用Ins:
package com.mx.mxdao;
import java.util.ArrayList;
import java.util.List;
public class Ins extends MxDaoData {
private int id;
private String data;
public int getId() {
return id;
}
public void setId(int id) {
this.id = id;
}
public String getData() {
return data;
}
public void setData(String data) {
this.data = data;
}
public String toString() {
return id + ":" + data;
}
public static void main(String[] args) {
Ins ins = new Ins();
ins.setData("da");
ins.setId(2222);
Ins ins3 = new Ins();
ins3.setData("daa");
ins3.setId(22223333);
List<Ins> ins2 = new ArrayList<>();
ins2.add(ins);
ins2.add(ins3);
try {
MxDaoManager.Select("id").find(Ins.class);
MxDaoManager.Where("id=?", "1").find(Ins.class);
MxDaoManager.limit("10").find(Ins.class);
MxDaoManager.orderby("id").find(Ins.class);
MxDaoManager.Select("id").Where("id=?", "1").limit("10").orderby("id").find(Ins.class);
MxDaoManager.findByColumn(Ins.class, "id", "1");
MxDaoManager.upDateByWhere(Ins.class, "id,name", "1,222");
MxDaoManager.Where("id=?", "1").upDateByWhere(Ins.class, "id,name", "1,222");
MxDaoManager.deleteByWhere(Ins.class, "id", "1");
System.out.println(MxJsonUtil.getJsonIns(0, "描述", ins));
} catch (Exception e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
是不是比起之前的操作简单多了,比较适合小型的项目使用
我放在了github上,刚兴趣的童孩可以看下MXDao