squirrel: SQL生成器

827 阅读2分钟

我正在参与掘金创作者训练营第6期,点击了解活动详情

SQL 真是个让人又爱又恨的东西,作为一个DSL(领域专用语言)来说,它是相当成功的,极强的表达能力让它在大数据分析中依然能够大放异彩,从 Spark 和 Flink 这样的流处理框架也要提供SQL功能上这点可见一斑。话是这么说,可到平日里后台逻辑上每次到要写具体的SQL时又让人提不起兴致。大抵是因为SQL太灵活放荡,而Go这种命令化的语言又太过保守,所以才让具体逻辑里的两者显得那样格格不入。

当业务逻辑中仅仅需要简单的查询条件时,大材小用之下,SQL便成了折磨。为了逃避这种折磨,就需要SQL生成器来解放我们。

今天要说的就是Go语言SQL生成器: squirrel 这个第三方库。

它功能上比较简单,并没有ORM那种程度,大包大揽所有的功能,堪堪做到了SQL语句的生成这一个功能,用以配合database/sql或者它的衍生库使用。说句题外话,Go的ORM真没有那种能让人眼前一亮的,SQL生成部分和本文这个比起来大多也就是伯仲之间而已,没有能让人感受到Java的Mybatis甚至时JPA那种酣畅的ORM框架。

squirrel 在SQL生成的做法是把几个子句标识符都做成了函数,比如Select,Insert,Where,From,Limit 以查询id 等于某几个值的SQL语句。以1,3,5为例,语句应该如下:

SELECT id, name FROM target where id in (1,3,5);

由于需要避免SQL注入,1,3,5这样的参数在实际中需要使用占位符,并且这里其实应该是变长参数。加入使用squirrel 这个库写法则如下:

squirrel.Select("id","name").From("target").Where(squirrel.Eq{"id",ids}).ToSql()

条件控制部分squirrel稍微有些放飞,使用一个哈希表记录。比如上面这种相对比较复杂的In语句构造,它也可以直接当作Equal这种类型,不过ids是一个列表。 其他的增删改查就不一一展开了,个人认为他对得起它的宣传标语:“Fluent SQL generation for golang ”。

比较可惜的是它的实现大量使用了interfact{}这种,在类型处理上有点弱。但这是Go自己的问题,虽然1.18版本勉强做了泛型,在这些方面还是对象映射这些方面还是没有太多用途。