一 . 基礎規範
1.必須使用InnoDB存儲引擎android
解讀:支持事務;支持行級鎖;支持MVCC多版本控制;支持外鍵;死鎖自動檢測;併發性能更好、CPU及內存緩存頁優化使得資源利用率更高。ios
2. 表字符集推薦使用utf8mb4sql
解讀:utf8 是 Mysql 中的一種字符集,只支持最長三個字節的 UTF-8字符,也就是 Unicode 中的基本多文本平面(BMP)。任何不在基本多文本平面的 Unicode字符,都沒法使用 Mysql 的 utf8 字符集存儲。包括 Emoji 表情(Emoji 是一種特殊的 Unicode 編碼,常見於 ios 和 android 手機上),和不少不經常使用的漢字,以及任何新增的 Unicode 字符等等。要在 Mysql 中保存 4 字節長度的 UTF-8 字符,須要使用 utf8mb4 字符集,utf8mb4是utf8的超集,有存儲4字節例如表情符號時,使用它。數據庫
3. 數據表、數據字段必須加入中文註釋緩存
解讀:方便你們對錶的理解,方便DBA和開發的溝通,方便歷史傳承。服務器
4. 禁止使用存儲過程、視圖、觸發器、Event架構
解讀:A.對數據庫性能影響較大,互聯網業務,能讓站點層和服務層乾的事情,不要交到數據庫層,數據庫擅長存儲和索引。併發
B.調試,排錯,遷移都比較困難,擴展性較差。函數
5. 禁止存儲大文件或者大照片高併發
解讀:建議存儲到專門的類型數據庫中。
6.MySQL 服務配置時,明確server_id
In MySQL 5.7, a server ID had to be specified when binary logging was enabled, or the server would not start. In MySQL 8.0, the server_id
system variable is set to 1 by default. The server can be started with this default ID when binary logging is enabled, but an informational message is issued if you do not specify a server ID explicitly using the --server-id
option. For servers that are used in a replication topology, you must specify a unique nonzero server ID for each server.
二 . 命名規範
1. 庫名,表名,列名必須用小寫,採用下劃線分隔
解讀:A.數據庫服務器端開了大小寫敏感,提升數據庫服務器性能
B.只有一套標準,避免Abc,ABC混淆(SQL)
2. 庫名,表名,列名必須見名知義,長度不要超過32字符
解讀:見名知義,便於理解;長度不要過長,便於書寫。
三 . 表設計規範
1. 表必須有主鍵,推薦使用bigint,表數據量少也可以使用unsigned int爲主鍵
解讀:刪除無主鍵的表,若是是row模式的主從架構,從庫會掛住
2. 主從表可以使用自增bigint作主鍵,冗餘無業務含義的字段作關聯字段,並作非彙集索引
解讀:A.如order表自增主鍵id,冗餘order_no字段,order_detail表自增主鍵id,冗餘order_no字段;order\order_detail和經過order_no關聯,並對order_no作非彙集索引
B.可有效減小數據文件和索引文件提示查詢性能
3. 禁止使用外鍵,若是要保證完整性,應由應用程式實現
解讀:外鍵使得表之間相互耦合,影響update/delete等SQL性能,有可能形成死鎖,高併發狀況下容易成爲數據庫瓶頸點
4. 建議將大字段,訪問頻度低的字段拆分到單獨的表中存儲,分離冷熱數據
解讀:會顯著提高該表的查詢性能
5. 表必須有字段create_by、create_time、modify_by、modify_time、disabled
解讀:便於表的維護。
四 . 列設計規範
1. 根據業務區分使用tinyint/int/bigint,分別會佔用1/4/8字
解讀:數據量大時,表字段的類型會顯著影響性能
2. 根據業務區分使用char/varchar
解讀:A.字段長度固定,或者長度近似的業務場景,適合使用char,可以減小碎片,查詢性能高
B.字段長度相差較大,或者更新較少的業務場景,適合使用varchar,可以減小空間
3. 根據業務區分使用datetime(3)/timestamp(3)
解讀:A.前者佔用8個字節,後者佔用4個字節,存儲年使用YEAR,存儲日期使用DATE,存儲時間使用datetime(3)
B.若是須要根據時區顯示對應時區的時間,使用timestamp
C.Datetime(3)/timestamp(3)保存到毫秒級別,程序端select now(3)
4. 必須把字段定義爲NOT NULL並設默認值
解讀:A.NULL的列使用索引,索引統計,值都更加複雜,MySQL更難優化
B.NULL須要更多的存儲空間
C.NULL只能採用IS NULL或者IS NOT NULL,不可以使用=/!=/in/not in
5. 使用varchar(20)存儲手機號,不要使用整數
解讀:A.牽扯到國家代號,可能出現+/-/()等字符,例如+86
B.手機號不會用來作數學運算
C.varchar能夠模糊查詢,例如like ‘138%’
6. 使用TINYINT來代替ENUM
解讀:ENUM增長新值要進行DDL操做
五 . 索引規範
1. 非彙集索引使用idx_[字段名]來命名
2. 單張表索引數量建議控制在5個之內
解讀:A.互聯網高併發業務,太多索引會影響寫性能
B.生成執行計劃時,若是索引太多,會下降性能,並可能致使MySQL選擇不到最優索引
C.異常複雜的查詢需求,能夠選擇其餘等更爲適合的方式存儲
3. 儘可能避免\禁止使用惟一索引
解讀:只是比非彙集索引快一個CPU查找的時間,但在delete,update時都要從新排序
4. 組合索引字段數不建議超過3個
解讀:若是3個字段還不能極大縮小row範圍,極可能是設計有問題
5. 不建議在頻繁更新的字段上創建索引
6. 非必要不要進行JOIN查詢,若是要進行JOIN查詢,被JOIN的字段必須類型相同,並創建索引
解讀: JOIN字段類型不一致,會致使全表掃描。
7. 理解組合索引最左前綴原則,避免重複建設索引,若是創建了(a,b,c),至關於創建了(a), (a,b), (a,b,c)
六 . SQL語句規範
1. 禁止使用select *,只獲取必要字段
解讀:A.select *會增長cpu/io/內存/帶寬的消耗
B.指定字段能有效利用索引覆蓋
C.指定字段查詢,在表結構變動時,能保證對應用程序無影響
2. insert必須指定字段,禁止使用insert into T values()
解讀:指定字段插入,在表結構變動時,能保證對應用程序無影響
3. 隱式類型轉換會使索引失效,致使全表掃描
解讀:必定要確保聲明的類型和索引字段類型一致
4. 禁止在where條件列使用函數或者表達式
解讀:致使不能命中索引,全表掃描
5. 禁止%開頭的模糊查詢
解讀:致使不能命中索引,全表掃描
6. 儘量不使用大表JOIN和子查詢
解讀:會佔用大量的內存、IO、CPU,若是使用到要先縮小結果集在作join(超過1000萬的表都應該考慮縮小結果集在作join)
7. 區分INNER\LEFT\RIGHT\FULL JOIN,合理使用,JOIN儘可能不超過3個表
解讀:MySQL查詢優化器很爛,可在測試環境構造不一樣的寫法,查看對應的執行計劃,得出最佳的方案,可以使用測試環境最佳實踐
8. 同一個字段上的OR必須改寫爲IN,IN的值必須少於50個
9. 應用程序必須捕獲SQL異常
解讀:方便定位線上問題