最新消息:XAMPP默认安装之后是很不安全的,我们只需要点击左方菜单的 "安全"选项,按照向导操作即可完成安全设置。

一种巧妙的对象映射关系设计–JSON-ORM

XAMPP下载 admin 1104浏览 0评论
 项目介绍
这是标准数据库封装的上半部分,智能查询(JSON-ORM)的实现。完整代码:https://github.com/zhoutk/gels

设计思路
我们通用的ORM,基本模式都是想要脱离数据库的,几乎都在编程语言层面建立模型,由程序去与数据库打交道。虽然脱离了数据库的具体操作,但我们要建立各种模型文档,用代码去写表之间的关系等等操作,让初学者一时如坠云雾。我的想法是,将关系数据库拥有的完善设计工具之优势与微服务结合起来,数据设计提供结构信息;前端送到后端的json对象自动映射成为标准的SQL查询语句。只要我们理解了标准的SQL语言,我们就能够完成数据库查询操作。我的这种ORM方式,服务端不需要写一行代码,只需完成关系数据库的设计,就能为前端提供标准服务接口。并且遵循一套统一的接口(已经实践检验,满足百分之九九的查询需求)来实现数据库封装,达到业务层可以随意切换数据库的目的。

数据库查询操作接口。
export default interface IDao {
select(tablename: string, params: object, fields?: Array<string>): Promise<any>;                            //自动生成sql语句
execSql(sql: string, values: Array<any>, params: object, fields?: Array<string>): Promise<any>;             //执行手动sql语句
}
智能查询(JSON-ORM)
查询保留字:fields, page, size, sort, search, lks, ins, ors, count, sum, group
fields, 定义查询结果字段,支持数组和逗号分隔字符串两种形式
由前端来确定返回的数据库字段信息,这样后端的设计可以适用面更广泛,而不会造成网络带宽的浪费。
在KOA2的框架下,GET请求要支持输入数组,只能把同一个key多次输入,如:age=11&age=22。这样很不方便,我实现了一个参数转换函数,针对数组提供多种输入形式。
arryParse

arryParse(arr): Array<any>|null {                      //返回值为数据或空值
try {
if (Array.isArray(arr) || G.L.isNull(arr)) {   //如果输入是数组或空,直接返回
return arr
} else if (typeof arr === ‘string’) {          //若是字符串
if (arr.startsWith(‘[‘)) {                 //数组的字符串形式,进行转换
arr = JSON.parse(arr)
} else {
//逗号拼接的字符串,mysql的驱动同时支持参数以字符串形式或数组形式提供,
//所以这里可以不加判断,直接用split函数将字符串转化为数组
arr = arr.split(‘,’)
}
}
} catch (err) {
arr = null            //数组的字符串形式转换失败,刘明输入参数是错误的
}
return arr
}
查询示例:

请求URL:  /rs/users?username=white&age=22&fields=[“username”,”age”]
生成sql:   SELECT username,age FROM users  WHERE username = ?  and age = ?
page, size, sort, 分页排序
在mysql中这比较好实现,limit来分页是很方便的,排序只需将参数直接拼接到order by后就好了。
查询示例:

请求URL:  /rs/users?page=1&size=10&sort=age desc
生成sql:   SELECT * FROM users  ORDER BY age desc LIMIT 0,10
search, 模糊查询切换参数,不提供时为精确匹配
提供字段查询的精确匹配与模糊匹配的切换,实现过程中,注意参数化送入参数时,like匹配,是要在参数两边加%,而不是在占位符两边加%。
另外,同一个字段匹配两次模糊查询,需要特别处理,我提供了一种巧妙的方法:

//将值用escape编码,数组将转化为逗号连接的字符串,用正则全局替换,变成and连接
value = pool.escape(value).replace(/\’, \’/g, “%’ and ” + key + ” like ‘%”)
//去掉两头多余的引号
value = value.substring(1, value.length – 1)
//补齐条件查询语句,这种方式,比用循环处理来得快捷,它统一了数组与其它形式的处理方式
where += key + ” like ‘%” + value + “%'”
查询示例

请求URL: /rs/users?username=i&password=1&search
ins, lks, ors
这是最重要的三种查询方式,如何找出它们之间的共同点,减少冗余代码是关键。

ins, 数据库表单字段in查询,一字段对多个值,例:
查询示例:

请求URL:  /rs/users?ins=[“age”,11,22,26]
生成sql:   SELECT * FROM users  WHERE age in ( ? )
ors, 数据库表多字段精确查询,or连接,多个字段对多个值,支持null值查询,例:
查询示例:

请求URL:  /rs/users?ors=[“age”,1,”age”,22,”password”,null]
生成sql:   SELECT * FROM users  WHERE  ( age = ?  or age = ?  or password is null )
lks, 数据库表多字段模糊查询,or连接,多个字段对多个值,支持null值查询,例:
查询示例:

请求URL:  /rs/users?lks=[“username”,”i”,”password”,null]
生成sql:   SELECT * FROM users  WHERE  ( username like ?  or password is null  )
count, sum
这两个统计求和,处理方式也类似,查询时一般要配合group与fields使用。

count, 数据库查询函数count,行统计,例:
查询示例:

请求URL:  /rs/users?count=[“1″,”total”]&fields=[“username”]
生成sql:   SELECT username,count(1) as total  FROM users
sum, 数据库查询函数sum,字段求和,例:
查询示例:

请求URL: /rs/users?sum=[“age”,”ageSum”]&fields=[“username”]
group, 数据库分组函数group,例:
查询示例:

请求URL:  /rs/users?group=age&count=[“*”,”total”]&fields=[“age”]
生成sql:   SELECT age,count(*) as total  FROM users  GROUP BY age
不等操作符查询支持
支持的不等操作符有:>, >=, <, <=, <>, =;逗号符为分隔符,一个字段支持一或二个操作。
特殊处:使用”=”可以使某个字段跳过search影响,让模糊匹配与精确匹配同时出现在一个查询语句中

一个字段一个操作,示例:
查询示例:

请求URL:  /rs/users?age=>,10
生成sql:   SELECT * FROM users  WHERE age> ?
一个字段二个操作,示例:
查询示例:

请求URL:  /rs/users?age=>,10,<=,35
生成sql:   SELECT * FROM users  WHERE age> ? and age<= ?
使用”=”去除字段的search影响,示例:
查询示例:

请求URL:  /rs/users?age==,22&username=i&search
生成sql:   SELECT * FROM users  WHERE age= ?  and username like ?

转载请注明:XAMPP中文组官网 » 一种巧妙的对象映射关系设计–JSON-ORM

您必须 登录 才能发表评论!