SQL反模式-主键

1 合理使用主键的反模式
如果你设计过数据库,首要就是要明白主键的作用,当然不限于以下的几种理由
a、确保数据行在整张表的唯一性
b、快速定位到一条记录
c、被外键引用来建立表与表之间的关系。
如何设计主键呢?很多书或框架将主键做了一个约束
a、主键的列名叫做id
b、数据类型是32位或64位整型(我并不认可这种做法,因为可以使用32位uuid或36位id)。
c、主键的值是自动生成的来确保唯一的。
Bill Karwin著的《SQL反模式》则认为上面说的是反模式,也就是不合理。如果针对一个初、中级开发工程师,那么我认为Bill Karwin是对的,的确,会对他们产生误导,以为id成为了主键的同义词,而且认为id作为表的伪主键是必要的,所以Karwin建议使用有意义的关键字作为主键,或者使用联合主键。
不过还好Karwin并没有把话完全说死,合理使用反模式是值得认可的。
我的最佳实践是使用id作为所有表的主键,这个id类似java的泛型的概念,采购订单号是id,用户-角色关系表用id作为伪主键,尽管它毫无意义;员工编号也使用id。
为什么这么做的呢
我首先反问你认为使用bug_id作为主键有意义,那么该表的其他字段是否都应该加上前缀bug_呢?Oracle对表名有长度限制,如果你强制每个字段都加上表名作为前缀,很容易你就超出了限额。
然后我想说的是,“厚平台、薄应用”的思想,你就知道管理系统支撑起了平台应用核心,管理系统的快速迭代也势必影响了建立平台之上应用的发展速度了。
扯这么多其他是想告诉你,设计数据表,将某些字段名称通过你的最佳实践固定起来,形成规范,那么你就可以通过velocity、freemarker等方式自动生成代码,那么你做系统的时候,大部分代码就可以自行完成了,是不是很酷。
我的设计就是使用id作为主键(32位uuid),后续我将告诉大家如何使用velocity写自动生成代码,其实很简单。08年左右很多公司,例如普元、金蝶EAS等都有自己的代码生成框架,这些在我看来都过于臃肿,我要做的是轻量,稍作调整,不把开发人员搞废了。
2 不使用联合主键
我一般不使用联合主键,为什么呢?如果附录中的用户-角色关系表,原本可以使用user_id、role_id作为联合主键,就可以很好的控制用户-角色关系的唯一性,那么为什么非要加了一个id作为伪主键呢?
如果你使用过mybatis generator,您可以看看下面生成java pojo的代码示例
从下图我们可以看出mybatis generator将联合主键生成一个SmsTestKey的pojo,然后你在SmsTestMapper中如果你想获取某一条数据,你还得将通过一个对象SmsTestKey来获取这条数据,想想一下你的js和controller写起来将会有多难?而联合主键对我们产生的意义真是甩了好几条街。当不值mybatis generator,hibernate的生成也是同样的策略。
因此通过
易用性的权衡
,如果你使用的java,不是Ruby on Rails或者php,我的建议是不采用联合主键,让程序更轻量,尽管不使用数据库的联合主键是一种反模式,但开发程序并不单靠数据库发挥作用。
联合主键的pojo
联合主键的Dao
附录
下面有三张表用户表、角色表、用户-角色关系表,用户与角色是一对多的关系,故而使用用户-角色关系表来表示。
用户表
ucs_user表
角色表
ucs_role表
用户-角色关系表
ucs_user_role

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

warrah

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值