Firebase Realtime Database là cơ sở dữ liệu NoSQL đám mây của Google với khả năng đồng bộ hóa thay đổi theo thời gian thực qua kết nối WebSocket liên tục. Dữ liệu được lưu trữ dưới dạng một cây JSON duy nhất và mọi thay đổi trên bất kỳ nút nào đều được chuyển ngay lập tức đến tất cả các máy khách đã kết nối. Theo Google, 2026, Realtime Database hỗ trợ tới 200 nghìn kết nối đồng thời tới một phiên bản. Dịch vụ được cung cấp với giới hạn miễn phí 1 GB bộ nhớ và 10 GB lưu lượng mỗi tháng.
Những điểm chính
Firebase Realtime Database là một trong những cơ sở dữ liệu thời gian thực đám mây đầu tiên, được Google ra mắt cùng với Firebase vào năm 2012. Đây là cơ sở dữ liệu NoSQL nơi dữ liệu được lưu trữ dưới dạng một cây JSON duy nhất có thể truy cập qua một URL. SDK máy khách (Android, iOS, Web) đăng ký vào các nút cụ thể của cây qua WebSocket và nhận cập nhật mỗi khi dữ liệu thay đổi — mà không cần thăm dò máy chủ hay triển khai cơ chế Push tùy chỉnh.
Firebase ban đầu được thành lập vào năm 2011 bởi James Tamplin và Andrew Lee, và sản phẩm đầu tiên chính là Realtime Database. Sau khi được Google mua lại vào năm 2014 (theo TechCrunch — với số tiền từ 50 đến 100 triệu đô la), cơ sở dữ liệu đã được tích hợp vào Google Cloud và đạt được thông lượng cao hơn đáng kể. Năm 2017, Google công bố Firestore như một sự thay thế tiến hóa, nhưng Realtime Database vẫn tiếp tục được hỗ trợ và cập nhật tích cực. Theo Google (2026), Realtime Database vẫn được sử dụng trong hơn 1,5 triệu dự án đang hoạt động.
Gói Spark (miễn phí) bao gồm: 1 GB bộ nhớ, 10 GB dữ liệu tải xuống mỗi tháng, 100 kết nối đồng thời và hỗ trợ cơ sở dữ liệu tại một khu vực. Trên gói Blaze (trả theo mức sử dụng), phí được tính cho bộ nhớ bổ sung ($1/GB), lưu lượng ($0.12/GB) và kết nối đồng thời ($5 cho mỗi 100 nghìn vượt quá giới hạn). Để thử nghiệm, cũng có chế độ mô phỏng — firebase emulators:start — chạy Realtime Database cục bộ mà không kết nối với đám mây.
Realtime Database không có bảng, bộ sưu tập hay tài liệu — mọi thứ là một cây JSON duy nhất có thể truy cập qua URL như https://project-name-default-rtdb.firebaseio.com/. Mỗi khóa trong cây hoặc là giá trị cuối cùng (chuỗi, số, boolean, null) hoặc là nút lồng nhau với các khóa con. Cơ sở dữ liệu không hỗ trợ JOIN, truy vấn con hay tổng hợp — một truy vấn luôn trả về nội dung của một nút với tất cả các phần tử con của nó.
Do thiếu JOIN trong Realtime Database, chuẩn hóa dữ liệu là bắt buộc. Thay vì cây lồng nhau (người dùng → danh sách bài đăng của họ), dữ liệu được chia thành các danh sách phẳng với tham chiếu qua các khóa. Đây là cách tiếp cận tiêu chuẩn: dữ liệu được phi chuẩn hóa để việc đọc một nút không kéo theo toàn bộ ngữ cảnh. Ví dụ: danh sách tin nhắn chat được lưu trữ riêng với hồ sơ người dùng và mỗi bài đăng chỉ chứa ID của tác giả, không phải toàn bộ hồ sơ của họ.
| Cách tiếp cận | Ví dụ cấu trúc | Vấn đề |
|---|---|---|
| Lồng nhau | users/{uid}/posts/{postId}/content | Đọc người dùng tải tất cả bài đăng |
| Phẳng | posts/{postId}/authorId + users/{uid}/name | Yêu cầu hai truy vấn |
| Phi chuẩn hóa | posts/{postId}/authorName (sao chép) | Trùng lặp khi cập nhật |
Truy vấn trong Realtime Database được thực hiện bằng bộ lọc (orderByChild, orderByKey, orderByValue, limitToFirst, limitToLast, equalTo, startAt, endAt). Không giống Firestore, chỉ mục được tạo thủ công qua phần Rules (.indexOn). Nếu chỉ mục không được khai báo, truy vấn có sắp xếp trả về lỗi PERMISSION_DENIED. Truy vấn chỉ hoạt động trên một trường duy nhất — truy vấn kết hợp (lọc theo giá + sắp xếp theo ngày) không được hỗ trợ. Để lọc phức tạp, dữ liệu thường được sao chép trong các nút khác nhau với các khóa sắp xếp khác nhau.
Lựa chọn giữa Realtime Database và Firestore là một trong những quyết định kiến trúc phổ biến khi bắt đầu dự án. Google khuyên dùng Firestore cho hầu hết các ứng dụng mới, nhưng Realtime Database vẫn là lựa chọn tốt nhất cho các tình huống mà độ trễ truyền dữ liệu tối thiểu là rất quan trọng.
Tình huống thứ nhất — trò chơi nhiều người chơi với đồng bộ hóa trạng thái (cờ vua, trò chơi bài, hành động thời gian thực). Độ trễ của Realtime Database là 10-30 ms so với 50-100 ms của Firestore trong cùng khu vực. Tình huống thứ hai — trò chuyện và nhắn tin với tần suất tin nhắn cao. Realtime Database được tính phí theo khối lượng dữ liệu, không phải số lần ghi, khiến nó rẻ hơn đáng kể so với Firestore ở tần suất trên 1 tin nhắn mỗi giây. Tình huống thứ ba — sự hiện diện của người dùng trực tuyến/ngoại tuyến, nơi trình xử lý onDisconnect của Realtime Database cho phép đặt trạng thái một cách nguyên tử khi mất kết nối.
Theo Google (2026), khoảng 15% dự án Firebase mới có ý thức chọn Realtime Database — khi nhóm hiểu rõ yêu cầu về độ trễ, cấu trúc dữ liệu và ngân sách. Trong 85% trường hợp còn lại, Firestore là lựa chọn an toàn hơn nhờ khả năng mở rộng tốt hơn, truy vấn mạnh mẽ hơn và sao chép tự động.
Kết nối Realtime Database với ứng dụng Android được thực hiện bằng cách thêm phụ thuộc firebase-database-ktx trong build.gradle. Đối tượng FirebaseDatabase có sẵn qua getInstance(url) — bạn có thể kết nối với nhiều cơ sở dữ liệu trong cùng một dự án Firebase. Sau khi khởi tạo, SDK tự động thiết lập kết nối WebSocket với máy chủ và bắt đầu đồng bộ hóa dữ liệu.
dependencies {
implementation(platform("com.google.firebase:firebase-bom:33.1.0"))
implementation("com.google.firebase:firebase-database-ktx")
}
// Initialization with custom URL
val database = FirebaseDatabase.getInstance(
"https://my-project-default-rtdb.firebaseio.com/"
)
val ref = database.getReference("chats")
Realtime Database sử dụng đối tượng DatabaseReference cho mọi thao tác. setValue() ghi dữ liệu vào nút được chỉ định, thay thế hoàn toàn toàn bộ nội dung của nó. push() tự động tạo một khóa duy nhất (dựa trên dấu thời gian) để thêm mục vào danh sách — đây là cách tiêu chuẩn để tạo tin nhắn chat, bài đăng và bản ghi. updateChildren() sửa đổi nhiều nút một cách nguyên tử trong một thao tác duy nhất. addValueEventListener đăng ký thay đổi nút và nhận callback mỗi khi dữ liệu được cập nhật.
data class Message(
val author: String = "",
val text: String = "",
val timestamp: Long = ServerValue.TIMESTAMP
)
class ChatRepository(private val ref: DatabaseReference) {
fun sendMessage(author: String, text: String) {
val msg = Message(author = author, text = text)
ref.child("messages").push().setValue(msg)
}
fun observeMessages(): Flow<List<Message>> = callbackFlow {
val listener = ref.child("messages")
.addValueEventListener(object : ValueEventListener {
override fun onDataChange(snapshot: DataSnapshot) {
val messages = snapshot.children.mapNotNull { it.getValue(Message::class.java) }
trySend(messages)
}
override fun onCancelled(error: DatabaseError) {}
})
awaitClose { ref.removeEventListener(listener) }
}
}
Cơ chế đồng bộ hóa của Realtime Database dựa trên giao thức WebSocket (trước đây — thăm dò dài). Máy khách gửi yêu cầu đăng ký một nút cụ thể và máy chủ giữ kết nối mở. Khi có bất kỳ thay đổi dữ liệu nào trong nút đã đăng ký, máy chủ sẽ gửi toàn bộ JSON của nút đó cho máy khách. SDK trên máy khách tự động cập nhật trạng thái cục bộ và kích hoạt các callback tương ứng (onDataChange).
OnDisconnect là một tính năng độc đáo của Realtime Database không có trong Firestore. Nhà phát triển có thể đăng ký một thao tác ghi sẽ tự động được thực thi trên máy chủ khi kết nối của máy khách bị mất. Điều này được sử dụng cho trạng thái hiện diện: “user123/status”: “online” với onDisconnect.setValue(“offline”). Nếu người dùng đóng ứng dụng hoặc mất internet, máy chủ sẽ tự động đặt trạng thái thành “offline” trong vòng tối đa 3 phút (có thể cấu hình trong bảng điều khiển Firebase).
Persistence trong Realtime Database được kích hoạt bằng một dòng: FirebaseDatabase.getInstance().setPersistenceEnabled(true). SDK lưu trạng thái cuối cùng của tất cả các nút đã đăng ký vào bộ nhớ đệm trên đĩa (mặc định tới 10 MiB, có thể cấu hình tới 100 MiB). Khi mất kết nối, máy khách tiếp tục làm việc với dữ liệu đã lưu trong bộ nhớ đệm và tất cả các thao tác ghi được xếp vào hàng đợi. Khi kết nối được khôi phục, SDK gửi tất cả các thay đổi tích lũy đến máy chủ theo đúng thứ tự (FIFO).
Theo Google (2026), các ứng dụng có bộ nhớ đệm liên tục được kích hoạt sẽ ít mất dữ liệu người dùng hơn 40% khi mất kết nối. Tuy nhiên, nếu máy khách tích lũy hơn 1000 thao tác đang chờ xử lý, máy chủ có thể từ chối tất cả và yêu cầu đồng bộ hóa đầy đủ — đây là cơ chế bảo vệ chống lại các máy khách lỗi thời.
Quy tắc bảo mật trong Realtime Database là cấu hình JSON mô tả ai có thể đọc và ghi dữ liệu trong mỗi nút và trong điều kiện nào. Các quy tắc chạy trên máy chủ của Google và được thực thi trước mỗi thao tác. Theo mặc định (trong sản xuất), nên đặt quy tắc ở chế độ “đóng” — chỉ người dùng đã xác thực mới có quyền truy cập.
Các quy tắc của Realtime Database được viết dưới dạng JSON với các phần .read, .write, .validate, .indexOn. Không giống Firestore (sử dụng cú pháp match), Realtime Database sử dụng các đối tượng lồng nhau phản ánh cấu trúc dữ liệu. Các điều kiện kiểm tra auth (xác thực), data (dữ liệu hiện có), newData (dữ liệu mới khi ghi) và now (thời gian máy chủ). Quy tắc xác thực (.validate) cho phép kiểm tra kiểu, phạm vi giá trị và cấu trúc dữ liệu.
{
"rules": {
"users": {
"$uid": {
".read": "auth.uid === $uid",
".write": "auth.uid === $uid",
".validate": "newData.hasChildren(['name', 'email'])"
}
},
"messages": {
".indexOn": ["timestamp"],
"$msgId": {
".read": true,
".write": "auth.uid !== null",
".validate": "newData.child('text').isString() && newData.child('text').val().length <= 500"
}
}
}
}
Các quy tắc của Realtime Database được kế thừa theo kiểu thác đổ — nếu .read = false ở cấp cao nhất, thì tất cả các nút con đều không khả dụng để đọc bất kể quy tắc riêng của chúng. Firebase cung cấp trình mô phỏng quy tắc trong bảng điều khiển nơi bạn có thể kiểm tra các thao tác với các mã thông báo xác thực khác nhau trước khi triển khai. Luôn nên kiểm tra quy tắc trong trình mô phỏng — một lỗi trong quy tắc có thể mở quyền truy cập vào dữ liệu riêng tư của tất cả người dùng. Theo Google (2026), 40% rò rỉ dữ liệu trong các dự án Firebase là do quy tắc bảo mật được cấu hình không đúng.
Câu hỏi thường gặp
Tới 200 nghìn kết nối đồng thời tới một phiên bản cơ sở dữ liệu. Khi vượt quá giới hạn, các kết nối mới bị chặn. Để mở rộng quy mô, phân mảnh trên nhiều cơ sở dữ liệu được sử dụng.
Sử dụng onDisconnect — đăng ký thao tác ghi cho “offline” khi mất kết nối. Máy chủ sẽ tự động thực thi khi WebSocket bị gián đoạn. Theo dõi kết nối riêng biệt qua .info/connected.
Kiểm tra .indexOn trong Quy tắc bảo mật — nếu không có chỉ mục được khai báo, truy vấn với orderByChild sẽ trả về PERMISSION_DENIED. Đồng thời đảm bảo dữ liệu được ghi vào đúng nút và người đọc có quyền .read.
Bảng điều khiển Firebase cung cấp xuất từ Realtime Database sang Firestore chỉ với một nút. Cấu trúc JSON được chuyển đổi thành bộ sưu tập và tài liệu. Để di chuyển tùy chỉnh, hãy sử dụng SDK Admin.
Không, lưu trữ mật khẩu trong Realtime Database bị cấm theo quy tắc bảo mật của Google. Sử dụng Firebase Auth để xác thực — hàm băm mật khẩu được lưu trữ trong kho lưu trữ biệt lập không thể truy cập qua SDK Realtime Database.
Tóm tắt
Chúng tôi sẽ phát triển ứng dụng di động chìa khóa trao tay
IT Sectr tạo các ứng dụng iOS và Android cho các công ty khởi nghiệp và doanh nghiệp từ năm 2017. Chúng tôi sẽ tư vấn và đề xuất giải pháp tốt nhất cho bạn.
Đọc thêm