数据库设计规范(参考)

基础规范

  • 使用INNODB存储引擎。
    INNODB引擎是MySQL5.5版本以后的默认引擘,支持事务、行级锁,有更好的数据恢复能力、更好的并发性能,同时对多核、大内存、SSD等硬件支持更好,支持数据热备份等,因此INNODB相比MyISAM有明显优势。
  • 库、表字符集使用utf8mb4,核对(Collation)使用utf8mb4_unicode_ci。 所有表、字段都需要添加注释。
  • 单表数据量建议控制在5000W以内。 不在数据库中存储图像、文件等大数据。 禁止在线上做数据库压力测试。
  • 禁止从测试、开发环境直连生产环境数据库。 不在业务高峰期批量更新、查询生产环境数据库。 SQL关键字全部是大写,每个词只允许有一个空格。
  • 禁止在数据库中存储明文密码,把密码加密后存储。 一般建议使用一列顺序递增的 ID
  • 来作为主键(多对对关联表除外),信息创建时间和信息更新时间默认使用如下方式命名和创建:
`create_time` timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP,
`update_time` timestamp NULL DEFAULT NULL ON UPDATE CURRENT_TIMESTAMP,
或者使用框架默认或建议的字段名称。

命名规则

  • 不得使用汉语拼音进行命名,严格、正确使用英文单词进行命名(包括缩写方式)。
  • 库名、表名、字段名必须使用小写字母,并采用下划线分割,表名加业务系统名称前缀或组件、插件名前缀,如:entrust_roles,其中entrust是角色权限组件。如果有新旧对比字段,则旧字段不加“_old”,新字段后面加“_new”。
  • 所有数据库对象字符串禁止超过32个字符。 所有数据库对象必须见名知意。命名与业务、产品线等相关联。
  • 所有数据库对象禁止使用MySQL保留字。 临时库、表名必须以tmp为前缀,并以日期为后缀。例如 tmp_mydb_20130704。
  • 备份库、表必须以bak为前缀,并以日期为后缀。例如 bak_mydb_20130704。

库、表、字段设计规范

  • 拆分大字段和访问频率低的字段,分离冷热数据。 尽可能不使用TEXT、BLOB类型。
  • 用DECIMAL代替FLOAT和DOUBLE存储精确浮点数。例如与货币、金融相关的数据。(其实使用int整型保存货币金额更好)
  • 越简单越好:将字符转化为数字、使用TINYINT来代替ENUM类型。 所有字段均定义为NOT NULL。
  • 使用UNSIGNED存储非负整数。 使用VARBINARY存储大小写敏感的变长字符串或二进制内容。
  • 使用尽可能小的VARCHAR字段。VARCHAR(N)中的N表示字符数而非字节数。
  • 使用timestamp存储时间,区分使用DATETIME和TIMESTAMP。存储年使用YEAR类型。存储日期使用DATE类型。
  • 存储时间(精确到秒)建议使用TIMESTAMP类型。 用好数值类型字段
tinyint (1Byte)
smallint (2Byte)
mediumint (3Byte)
int (4Byte)
bigint (8Byte)

如果数值字段没有那么大,就不要用 bigint。

  • 用HASH进行散表,表名后缀使用十进制数,下标从0开始。
    按日期时间分表需符合YYYY[MM][DD][HH]格式,例如2013071601。年份必须用4位数字表示。例如按日散表user_20110209、按月散表user_201102。 采用合适的分库分表策略。例如千库十表、十库百表等。

索引规范

索引的数量要控制:

索引相关的几个概念: 点击查看

单张表中索引数量不超过5个。
单个索引中的字段数不超过5个。
对字符串使用前缀索引【了解前缀索引】,前缀索引长度不超过8个字符。
建议优先考虑前缀索引,必要时可添加伪列并建立索引。
索引名必须全部使用小写。
唯一索引按照“uniq_字段名称[_字段名称]”进用行命名。例如uniq_age_name。
非唯一索引按照“idx_字段名称[_字段名称]”进用行命名。例如idx_age_name。
组合索引建议包含所有字段名,过长的字段名可以采用缩写形式。例如idx_age_name_add。
表必须有主键,推荐使用UNSIGNED自增列作为主键。
唯一键由3个以下字段组成,并且字段都是整型时,可使用唯一键作为主键。其他情况下,建议使用自增列或发号器作主键。
分情况使用外键。
联表查询时,JOIN列的数据类型必须相同,并且要建立索引。
不在低基数列(字段值区分度不高)上建立索引,例如“性别”。
选择区分度大的列建立索引。组合索引中,区分度大的字段放在最前。
不对过长的VARCHAR字段建立索引。建议优先考虑前缀索引,或添加CRC32或MD5伪列并建立索引。
合理创建联合索引,(a,b,c) 相当于 (a) 、(a,b) 、(a,b,c)。
合理使用覆盖索引减少IO,避免排序。【覆盖索引是select的数据列只用从索引中就能够取得,不必读取数据行,换句话说查询列要被所建的索引覆盖。索引的字段不只包含查询列,还包含查询条件、排序等。】

主键准则

表必须有主键。
不使用更新频繁的列作为主键。
尽量不选择字符串列作为主键。
不使用UUID MD5 HASH这些作为主键(数值过于离散) 。
默认使非空的唯一键作为主键。
建议选择自增或发号器。

重要的SQL必须被索引

比如:
UPDATE、DELETE语句的WHERE条件列。
ORDER BY、GROUP BY、DISTINCT的字段。

多表JOIN的字段注意以下:

区分度最大的字段放在前面。
核心SQL优先考虑覆盖索引。
避免冗余和重复索引。
索引要综合评估数据密度和分布以及考虑查询和更新比例。

索引禁忌

不在低基数列上建立索引,例如“性别”。
不在索引列进行数学运算和函数运算。

尽量不使用外键。

外键用来保护参照完整性,可在业务端实现。
对父表和子表的操作会相互影响,降低可用性。

新建的唯一索引不能和主键重复。

索引字段的默认值不能为NULL

要改为其他的default或者空。NULL非常影响索引的查询效率。

反复查看与表相关的SQL,符合最左前缀的特点建立索引

多条字段重复的语句,要修改语句条件字段的顺序,为其建立一条联合索引,减少索引数量。

能使用唯一索引就要使用唯一索引,提高查询效率

SQL规范

  • sql语句尽可能简单,大的sql想办法拆成小的sql语句(充分利用QUERY CACHE和充分利用多核CPU) 。
  • 事务要简单,整个事务的时间长度不要太长。
  • 避免使用触发器、函数、存储过程。
  • 降低业务耦合度,为sacle out(横向扩展)、sharding(分区分表)留有余地。
  • 避免在数据库中进⾏数学运算(MySQL不擅长数学运算和逻辑判断) 。
  • 不要用select *,查询哪几个字段就select 这几个字段。
  • sql中使用到OR的改写为用 IN() ,or的效率没有in的效率高。
  • in里面数字的个数建议控制在1000以内。
  • limit分页注意效率。Limit越大,效率越低。可以改写limit,比如例子改写:
select id from tlimit 10000, 10; => select id from t where id > 10000 limit10;
  • 使用union all替代union。
  • 避免使⽤大表的JOIN。
  • 使用group by 分组、自动排序。
  • 对数据的更新要打散后批量更新,不要一次更新太多数据。
  • 减少与数据库的交互次数。
  • 注意使用性能分析工具: Explain(通过explain我们可以得知SQL语句的具体执行情况,索引使用等)、show profile(可以结合show命令查看执行状态。)、mysqlsla(通过慢日志查询可以知道哪些SQL语句执行效率低下)。
  • SQL语句不可以出现隐式转换,比如 select id from 表 where id=‘1’。
  • 在SQL语句中,禁止使用前缀是%的like。
  • 使用预编译语句,只传参数,比传递SQL语句更高效;一次解析,多次使用;降低SQL注入概率。
  • 禁止使用order by rand()。

你可能感兴趣的:(学习参考)