Xác định dữ liệu bằng các thực thể Room

Khi sử dụng thư viện lưu trữ dữ liệu Room để lưu trữ dữ liệu của ứng dụng, bạn xác định các thực thể để biểu thị những đối tượng mà bạn muốn lưu trữ. Mỗi thực thể tương ứng với một bảng trong cơ sở dữ liệu Room được liên kết và mỗi phiên bản của một thực thể đại diện cho một hàng dữ liệu trong bảng tương ứng.

Việc sử dụng các thực thể Room cho phép bạn xác định giản đồ cơ sở dữ liệu mà không cần viết bất kỳ mã SQL nào.

Phân tích một thực thể

Bạn xác định mỗi thực thể Room là một lớp được chú thích bằng @Entity. Một thực thể Room bao gồm các thuộc tính cho từng cột trong bảng tương ứng trong cơ sở dữ liệu, bao gồm một hoặc nhiều cột tạo nên khoá chính.

Mã sau đây là ví dụ về một thực thể xác định một bảng User với các cột cho mã nhận dạng, họ và tên:

@Entity
data class User(
    @PrimaryKey val id: Int,
    val firstName: String,
    val lastName: String
)

Theo mặc định, Room sử dụng tên lớp này làm tên bảng cơ sở dữ liệu. Nếu bạn muốn bảng có tên khác, hãy đặt thuộc tính tableName của chú thích @Entity. Tương tự, theo mặc định, Room sử dụng tên thuộc tính làm tên cột trong cơ sở dữ liệu. Nếu bạn muốn một cột có tên khác, hãy thêm chú thích @ColumnInfo vào thuộc tính và đặt thuộc tính name. Ví dụ sau đây minh hoạ tên tuỳ chỉnh cho một bảng và các cột của bảng:

@Entity(tableName = "users")
data class User(
    @PrimaryKey val id: Int,
    @ColumnInfo(name = "first_name") val firstName: String,
    @ColumnInfo(name = "last_name") val lastName: String
)

Xác định khoá chính

Bạn phải xác định một khoá chính cho mỗi thực thể Room để nhận dạng duy nhất từng hàng trong bảng cơ sở dữ liệu tương ứng. Để thực hiện việc này, hãy chú thích từng cột bằng @PrimaryKey:

@PrimaryKey val id: Int

Xác định khoá chính tổng hợp

Nếu muốn các bản sao của một thực thể được xác định là duy nhất bởi một tổ hợp gồm nhiều cột, bạn có thể xác định một khoá chính tổng hợp bằng cách liệt kê các cột đó trong thuộc tính primaryKeys của @Entity:

@Entity(primaryKeys = ["firstName", "lastName"])
data class User(
    val firstName: String,
    val lastName: String
)

Bỏ qua các thuộc tính

Theo mặc định, Room sẽ tạo một cột cho mỗi thuộc tính được xác định trong thực thể. Để ngăn Room duy trì một thuộc tính, hãy chú thích thuộc tính đó bằng @Ignore:

@Entity
data class User(
    @PrimaryKey val id: Int,
    val firstName: String,
    val lastName: String,
    @Ignore val picture: Bitmap? = null
)

Nếu một thực thể kế thừa các thuộc tính từ một thực thể mẹ, hãy sử dụng thuộc tính ignoredColumns của chú thích @Entity:

open class User {
    var picture: Bitmap? = null
}

@Entity(ignoredColumns = ["picture"])
data class RemoteUser(
    @PrimaryKey val id: Int,
    val hasVpn: Boolean
) : User()

Room hỗ trợ một số chú giải cho phép bạn tìm kiếm thông tin chi tiết trong các bảng cơ sở dữ liệu.

Hỗ trợ phương thức tìm kiếm toàn bộ văn bản

Nếu ứng dụng của bạn yêu cầu phương thức tìm kiếm toàn bộ văn bản (FTS) nhanh, hãy hỗ trợ các thực thể bằng một bảng ảo. Sử dụng phần mở rộng FTS3 hoặc FTS4 SQLite hoặc phần mở rộng FTS5 SQLite.

Để sử dụng khả năng này, hãy thêm chú thích @Fts3, @Fts4 hoặc @Fts5 vào một thực thể.

// Use `@Fts3` only if your app has strict disk space requirements.
@Fts4
@Entity(tableName = "users")
data class User(
    // Specifying a primary key for an FTS-table-backed entity is optional,
    // but if you include one, it must an INTEGER type and column name "rowid".
    @PrimaryKey @ColumnInfo(name = "rowid") val id: Long,
    @ColumnInfo(name = "first_name") val firstName: String
)

Để tuỳ chỉnh cách thông tin cơ sở dữ liệu được mã hoá thành mã thông báo trong các bảng FTS, hãy sử dụng lựa chọn tokenizer. Room cung cấp một số trình phân tích từ được tích hợp sẵn thông qua FtsOptions, bao gồm TOKENIZER_SIMPLE, TOKENIZER_PORTERTOKENIZER_UNICODE61:

@Fts4(tokenizer = FtsOptions.TOKENIZER_UNICODE61)
@Entity(tableName = "users")
data class User(
    @PrimaryKey @ColumnInfo(name = "rowid") val id: Long,
    @ColumnInfo(name = "first_name") val firstName: String
)

Room cung cấp một số lựa chọn khác để xác định các thực thể được FTS hỗ trợ, bao gồm thứ tự kết quả, xoá chỉ mục khỏi các cột và bảng được quản lý dưới dạng nội dung bên ngoài. Để biết thêm thông tin về các lựa chọn này, hãy xem tài liệu tham khảo FtsOptions.

Lập chỉ mục các cột cụ thể

Nếu đang sử dụng AndroidSQLiteDriver và cần hỗ trợ các phiên bản SDK không hỗ trợ các thực thể dựa trên bảng FTS3, FTS4 hoặc FTS5, bạn vẫn có thể lập chỉ mục cho một số cột nhất định trong cơ sở dữ liệu để tăng tốc độ truy vấn. Nếu bạn sử dụng BundledSQLiteDriver, Room sẽ hỗ trợ tất cả các phiên bản FTS bất kể phiên bản SDK Android.

Để thêm chỉ mục vào một thực thể, hãy đưa thuộc tính indices vào chú giải @Entity. Liệt kê tên cột để đưa vào chỉ mục hoặc chỉ mục tổng hợp. Đoạn mã sau đây cho biết cách thêm chỉ mục:

@Entity(indices = [Index(value = ["last_name", "address"])])
data class User(
    @PrimaryKey val id: Int,
    @ColumnInfo(name = "first_name") val firstName: String,
    @ColumnInfo(name = "last_name") val lastName: String,
    val address: String?,
)

Đôi khi, một số cột hoặc nhóm cột trong cơ sở dữ liệu cần chứa các giá trị riêng biệt. Để thực thi tính duy nhất này, hãy đặt thuộc tính unique của chú thích @Index thành true. Mã mẫu sau đây cho biết cách thực thi tính duy nhất này:

@Entity(indices = [Index(value = ["first_name", "last_name"], unique = true)])
data class User(
    @PrimaryKey val id: Int,
    @ColumnInfo(name = "first_name") val firstName: String,
    @ColumnInfo(name = "last_name") val lastName: String,
)