1. Intro
(1) Thiết kế database là công việc thường ngày của engineer, nhất là các bạn database engineer. Giống với coding cần clean, database cũng cần tính chất tương tự nhằm giúp việc vận hành, thay đổi, chuyển giao nó đỡ tốn nhiều công sức hơn, do đó chúng ta cũng cần có một số quy tắc nhất định trong việc thiết kế.
Thường thì mỗi nhóm hay công ty sẽ có bộ quy tắc riêng cho mình, cho dù có được viết thành document rõ ràng hoặc không. Cũng giống như coding có nhiều trường phái khác nhau, ví dụ python thì có hai đại diện tiêu biểu là PEP8 và Google Python Style Guide, Database conventions cũng không nhất thiết phải tuân theo một chuẩn duy nhất, miễn sao nó mang lại những giá trị mà theo tôi là quan trọng nhất: Sự thống nhất (Consistency) và Dễ hiểu (Simplicity, Self-explaining)
(2) Đã bao giờ bạn nhìn vào thiết kế DB của hệ thống cũ khi gia nhập vào một công ty mới hoặc khi bạn tham gia vào một team khác và tự hỏi những câu giống như dưới đây không?
- “WTF is this field?” (ca này hay gặp nhất :D)
- “Cái field
status
này có giá trị là 0-1 hay còn gì khác không?” (chẹp,SELECT DISTINCT
để tìm chân lý vậy) - (đang code) “Table
random
này thì PK làid
hayrandom_id
nhỉ?” (mở DB ra coi lại)
Well, cá nhân tôi đã gặp khá nhiều và trở thành ám ảnh khi phải tiếp cận với một hệ thống lớn và phức tạp (ví dụ có 1000 table chẳng hạn) mà lại thiếu document. Đừng hiểu nhầm, tôi không kỳ vọng một bộ document cực kỳ lớn tới mức tôi phải lấy nhiều dũng cảm mới có thể đọc hết cho 1000 table kia, hoặc mỗi khi muốn biết 1 field là gì lại phải giở tài liệu ra tìm kiếm. Phần lớn các field đều có thể hiểu nhanh được nếu đặt tên tốt và có lúc cũng cần giải thích ngắn gọn đi kèm. Đây là 1 ví dụ:
(3) Vậy có cần DB document hay không? Tôi nghĩ là vẫn cần. Mỗi business/domain có các đặc thù riêng, dẫn tới các data field cũng khá đặc biệt nên nếu tôi không tìm hiểu kỹ thì sẽ chẳng hiểu nổi nó là gì, tương tác với dữ liệu đó sao cho đúng, như ví dụ dưới đây:
(4) Sẽ dễ dàng hơn nếu ngay từ khi thiết kế, chúng ta tuân theo một quy tắc là làm sao lần sau đụng tới thì tốn ít effort nhất có thể. Nhiều quy tắc được tổng hợp và thống nhất trong team thì trở thành bộ Database Conventions của team đó.
Trong bài này tôi sẽ đề cập tới một số conventions mà tôi và team của mình hay dùng.
Xem thêm: Việc làm Database lương cạnh tranh hấp dẫn
2. DB Conventions
2.1. Một số quy tắc chung về đặt tên
Nên | Ví dụ | Không nên | Giải thích |
Tên là danh từ tiếng Anh | |||
Chỉ dùng danh từ số ít | inventory shelf octopus |
inventories octopodes shelves octopuses octopi |
Đỡ mất thời gian nghĩ |
Chỉ dùng lower_case |
customer |
customer |
|
Chỉ dùng dấu gạch dưới _ để nối các từ |
first_name |
FirstName firstName "First Name" |
– Dễ đọc hơn – Đỡ thắc mắc khi nào thì có chữ hoa, khi nào thì có gạch dưới |
Tên có tính tự giải thích. – Tránh dùng từ viết tắt – Tránh dùng kiểu dữ liệu thay cho tên |
middle_name blog .content amt |
mid_nm blog .text amount |
Dễ hiểu |
Tránh dùng từ khóa của SQL | display_order updated_at |
order date name |
Có thể bị báo lỗi syntax nếu không enquote |
Tên ngắn gọn, không nên dài quá 64 ký tự |
2.2. Table
Nên | Ví dụ | Không nên | Giải thích |
Đặt prefix cho các table liên quan | catalog_category catalog_product |
Tìm kiếm table dễ hơn | |
Thêm suffix _tmp cho các table dùng tạm trong tính toán nhưng không xóa |
catalog_product_price_tmp |
||
Thêm prefix tmp_ cho các table dùng tạm, có thể xóa |
tmp_im_calculating |
2.3. Column
2.3.1. Column
Nên | Ví dụ | Không nên | Giải thích |
Tránh thêm tiền tố không cần thiết | product .name |
product .product_name |
– Tên table đã nêu rõ context |
Thêm prefix is_ cho các field dạng YES/NO |
is_active is_delivered is_free_shipping |
active delivered free_shipping |
Nhìn field là biết chỉ có 2 giá trị |
Nên lưu các thời điểm thay đổi dữ liệu với từng record | created_at updated_at deleted_at |
Theo dõi tính toàn vẹn dữ liệu | |
Không đặt tên chứa kiểu dữ liệu | return_code |
int_return_code |
Kiểu dữ liệu có thể thay đổi: – date => timestamp – int => bigint |
2.3.2. Primary Key
Nên | Ví dụ | Không nên | Giải thích |
Chỉ nên dùng PK là id |
table .id |
table .table_id |
– Dễ nhớ – Giảm effort khi đổi tên table sau này |
Mỗi table nên có 1 PK, bên cạnh các UNIQUE KEY khác | PRIMARY KEY (id), UNIQUE KEY idx_unique (key1,key2) |
Làm việc với các record nhanh hơn | |
PK mặc định nên dùng kiểu Interger, Auto-increment |
2.3.3. Foreign Keys
Nên | Không nên | Giải thích |
Tên FK được kết hợp từ tên field và tên table mà nó tham chiếu tới | person_id là FK của table và field person.id |
Dễ hiểu |
Tùy chọn Cascading Update có thể dùng, nhưng Cascading Delete thì nên tránh | Giảm rủi ro khi lỡ xóa record ở main table khiến cho toàn bộ dữ liệu liên quan biến mất |
2.3.4. Indexes
Nên | Ví dụ | Giải thích |
Thêm prefix idx_ ở đầu | idx_created_at |
Dễ nhớ, nhất là khi ALTER TABLE mà không dùng GUI Tool |
3. Tổng kết
Có nhiều quy tắc để nhớ, tuy nhiên có thể dựa trên nguyên tắc thiết kế ban đầu là:
Be Consistent and Simple, don’t waste your brain any single second for any unnecessary thing
Bạn có best-practice hoặc các quy tắc nào khác hữu ích hơn cho việc thiết kế Database không? Nếu có hãy chia sẻ cho mọi người tại đây nhé!
Nguồn: kipalog