Room: konsep kunci, Entity, DAO dan bekerja dengan database

Penulis: IT Sectr Diterbitkan: 2026-05-04 Waktu membaca: 8 mnt

Room adalah pustaka untuk bekerja dengan SQLite di Android yang merupakan bagian dari Jetpack. Library ini menyediakan lapisan abstraksi di atas SQLite mentah, mengotomatiskan pembuatan tabel, eksekusi query, dan konversi data ke objek Kotlin dan Java. Menurut Android Developers, Room mengompilasi query SQL pada tahap build, memeriksa kebenaran sintaks dan hubungan antara Entity dan tabel.

Poin Utama

  • Room — pustaka ORM Jetpack untuk SQLite di aplikasi Android.
  • Entity — kelas yang dianotasi dengan @Entity, setiap instance sesuai dengan baris dalam tabel.
  • DAO — Data Access Object dengan metode beranotasi untuk query SQL.
  • Database — kelas abstrak yang mewarisi RoomDatabase, menghubungkan Entity dan DAO.
  • Migrasi — mekanisme perubahan skema database yang aman tanpa kehilangan data pengguna.

Apa itu Room dan mengapa diperlukan

Room adalah pustaka persistensi dari Android Jetpack yang menyediakan pemetaan objek-relasional untuk SQLite. Room memecahkan tiga masalah utama SQLite mentah: penulisan banyak kode boilerplate untuk membuat tabel, tidak adanya pemeriksaan query SQL pada tahap kompilasi, dan konversi manual Cursor ke objek.

Library ini menggunakan kompilator anotasi (kapt atau KSP) yang menghasilkan implementasi kelas abstrak RoomDatabase dan DAO pada tahap build. Ini menjamin bahwa kesalahan sintaks dalam SQL dan ketidakcocokan tipe terdeteksi sebelum aplikasi dijalankan, bukan saat runtime setelah dipublikasikan di Google Play.

Menurut Google I/O 2023, Room digunakan di 68% aplikasi Android yang bekerja dengan data lokal. Ini adalah standar penyimpanan data di perangkat yang direkomendasikan oleh Google untuk semua proyek baru — menggantikan SQLiteOpenHelper dan ContentProvider yang sudah usang.

Terapkan Room dalam proyek yang memerlukan caching lokal data server, mode offline, atau penyimpanan data pengguna terstruktur dengan kemampuan query SQL yang kompleks.

Room adalah bagian dari Android Jetpack dan secara resmi direkomendasikan oleh Google untuk semua proyek baru yang bekerja dengan data lokal. Tidak seperti Realm atau ObjectBox, Room menggunakan SQLite asli, yang menjamin kompatibilitas dengan alat pihak ketiga mana pun untuk bekerja dengan database — dari DB Browser hingga DataGrip. Pengembang dapat membuka file .db aplikasi dan menjalankan query SQL secara langsung, yang memudahkan debugging dan analisis data selama proses pengembangan.

Entity dan anotasi di Room

Entity adalah kelas data yang dianotasi dengan @Entity, yang diubah Room menjadi tabel database. Setiap bidang kelas menjadi kolom tabel, dan setiap instance menjadi baris. Room menggunakan refleksi untuk mengakses bidang, oleh karena itu anotasi @PrimaryKey diperlukan untuk pengidentifikasi wajib.

Anotasi dasar

Anotasi @Entity memberi tahu Room bahwa kelas adalah tabel. Parameter tableName menentukan nama tabel jika berbeda dari nama kelas. @PrimaryKey mendefinisikan kunci utama dengan kemungkinan pembuatan otomatis melalui autoGenerate = true.

kotlin
@Entity(tableName = "users")
data class User(
    @PrimaryKey(autoGenerate = true)
    val id: Int = 0,
    @ColumnInfo(name = "full_name")
    val name: String,
    @Ignore
    val tempData: String?
)

@ColumnInfo menentukan nama kolom dalam tabel jika berbeda dari nama bidang Kotlin. @Ignore mengecualikan bidang dari tabel — tidak akan disimpan ke database. @ForeignKey mendeskripsikan kunci asing untuk hubungan antar tabel dengan operasi kaskade saat penghapusan atau pembaruan.

Room mendukung objek bersarang melalui anotasi @Embedded. Bidang kelas bersarang dijabarkan menjadi kolom tabel induk dengan prefiks untuk menghindari konflik nama. Misalnya, kelas Address dengan bidang city dan street, yang disematkan dalam User, akan membuat kolom address_city dan address_street di tabel users, menghilangkan kebutuhan untuk membuat tabel terpisah untuk objek nilai sederhana.

Jenis konversi

Room hanya mendukung tipe primitif dan pembungkusnya. Untuk menyimpan daftar, Date, atau tipe kustom digunakan @TypeConverter — metode statis konversi antara tipe kustom dan primitif SQLite, misalnya antara List dan string JSON.

DAO dan query SQL

DAO (Data Access Object) adalah antarmuka atau kelas abstrak yang dianotasi dengan @Dao, berisi metode untuk mengakses data. Setiap metode dianotasi dengan operasi SQL: @Insert, @Update, @Delete atau @Query dengan query SQL eksplisit.

@Query dengan pemeriksaan saat kompilasi

Anotasi @Query menerima string SQL yang diperiksa oleh Room pada tahap kompilasi untuk kebenaran sintaks dan kesesuaian nama kolom dengan bidang Entity. Room mendukung query berparameter melalui sintaks :paramName.

kotlin
@Dao
interface UserDao {
    @Query("SELECT * FROM users WHERE id = :userId")
    suspend fun getUserById(userId: Int): User?

    @Insert(onConflict = OnConflictStrategy.REPLACE)
    suspend fun insertUser(user: User)

    @Query("SELECT * FROM users ORDER BY name ASC")
    fun getAllUsers(): Flow<List<User>>
}

@Insert mendukung strategi OnConflictStrategy untuk menangani konflik saat menyisipkan record duplikat. Flow sebagai tipe kembalian memberikan pembaruan UI reaktif pada setiap perubahan data dalam tabel — langganan secara otomatis dimulai ulang pada setiap INSERT, UPDATE atau DELETE.

@Transaction untuk operasi kompleks

Anotasi @Transaction menjamin eksekusi atomik beberapa operasi dalam satu blok transaksi. Room mengunci database selama eksekusi, mencegah kondisi balapan saat akses bersamaan dari beberapa thread.

Database dan migrasi skema

RoomDatabase adalah kelas abstrak yang menyatukan Entity dan DAO dalam satu titik akses ke database. Dibuat melalui Room.databaseBuilder dengan menentukan versi skema dan daftar kelas Entity. Instance database direkomendasikan untuk dibuat sebagai singleton melalui delegasi lazy untuk menghindari banyak koneksi.

Migrasi

Migrasi di Room adalah kelas Migration yang mendeskripsikan skrip SQL untuk transisi dari versi skema lama ke baru. Jika migrasi tidak disediakan saat perubahan skema, Room melempar IllegalStateException. Ini melindungi dari kehilangan data pengguna yang tidak disengaja saat pembaruan aplikasi.

kotlin
val migration_1_2 = object : Migration(1, 2) {
    override fun migrate(db: SupportSQLiteDatabase) {
        db.execSQL("ALTER TABLE users ADD COLUMN age INTEGER NOT NULL DEFAULT 0")
    }
}

val db = Room.databaseBuilder(
    getApplication(),
    AppDatabase::class.java,
    "app_database"
).addMigrations(migration_1_2)
 .build()

Untuk pengembangan dapat menggunakan fallbackToDestructiveMigration, yang menghapus database lama dan membuat yang baru saat versi tidak cocok. Mode ini hanya untuk debugging — dalam rilis produksi migrasi wajib ditulis.

Untuk menguji database, Room menyediakan kelas khusus Room.inMemoryTestBuilder, yang membuat database di memori RAM tanpa menyimpan ke disk. Setelah setiap tes selesai, database secara otomatis dimusnahkan, menjamin isolasi penuh skenario pengujian. Dalam kombinasi dengan pustaka android-arch-core-testing, pengembang dapat mengelola siklus hidup database dan memeriksa kebenaran migrasi tanpa perlu membersihkan status secara manual.

Kinerja Room secara langsung tergantung pada struktur query dan indeks. Untuk analisis query lambat, Room menyediakan flag enableQueryCallback, yang mencatat semua query SQL dengan waktu eksekusi. Pengembang dapat menggunakan log ini untuk menemukan query yang berjalan lebih dari 100 milidetik dan mengoptimalkannya dengan menambahkan indeks gabungan melalui anotasi @Index di @Entity atau menulis ulang subquery menjadi JOIN langsung menggunakan @Relation.

Room juga mendukung enkripsi database melalui SQLCipher. Menghubungkan pustaka net.zetetic:android-database-sqlcipher dan menggunakan SupportFactory sebagai pengganti standar memberikan enkripsi transparan semua data pada disk tanpa mengubah query DAO dan struktur Entity. Ini diperlukan untuk aplikasi yang bekerja dengan data pribadi pengguna dan memenuhi persyaratan GDPR serta undang-undang Rusia 152-FZ tentang perlindungan data pribadi. Kata sandi enkripsi dapat disimpan di Android Keystore untuk melindungi dari ekstraksi melalui alat pada perangkat yang di-root.

Room dengan Kotlin Coroutines dan Flow

Room secara native mendukung Kotlin Coroutines mulai versi 2.1. Metode DAO dapat berupa fungsi suspend yang menjalankan query di latar belakang tanpa memblokir thread utama. Room secara otomatis mengelola dispatcher, menggunakan Dispatchers.IO untuk query baca dan tulis.

Untuk query reaktif, Room mengembalikan Flow — aliran data dingin yang mengeluarkan nilai baru pada setiap perubahan tabel yang terpengaruh. ViewModel berlangganan ke Flow melalui stateIn atau collect, memastikan pembaruan UI otomatis tanpa pemberitahuan manual ke adapter.

Room juga mendukung Paging 3 melalui implementasi khusus PagingSource yang memuat data secara halaman dari SQLite. Ini efisien untuk daftar besar dengan ribuan record: Paging 3 hanya memuat baris yang terlihat di layar dan secara otomatis memperbaruinya saat ada perubahan di database.

Gunakan Paging 3 dengan Room saat menampilkan feed berita, log operasi, atau daftar produk dengan akses offline dan pengguliran tanpa batas.

Pertanyaan yang Sering Diajukan

Apa perbedaan Room dengan SQLiteOpenHelper?

Room mengotomatiskan pembuatan tabel, konversi Cursor ke objek, dan pemeriksaan SQL pada tahap kompilasi. SQLiteOpenHelper memerlukan penulisan skema manual, pemrosesan Cursor, dan tidak memiliki pemeriksaan query sebelum aplikasi dijalankan, yang meningkatkan risiko kesalahan.

Apakah perlu menulis migrasi untuk setiap perubahan skema?

Ya, saat perubahan Entity (menambah/menghapus bidang, mengubah tipe) diperlukan migrasi. Tanpanya Room melempar IllegalStateException saat startup. Untuk pengembangan dapat mengaktifkan fallbackToDestructiveMigration, tetapi dalam rilis skrip migrasi yang benar wajib hukumnya.

Apakah Room mendukung hubungan antar tabel?

Room mendukung @ForeignKey untuk operasi kaskade dan @Relation untuk objek bersarang. Untuk query JOIN yang kompleks, gunakan anotasi @Transaction dengan @Query yang mengembalikan POJO dengan entitas bersarang melalui @Embedded dan @Relation.

Bisakah Room digunakan dengan Java tanpa Kotlin?

Ya, Room sepenuhnya kompatibel dengan Java. Alih-alih fungsi suspend, gunakan LiveData atau RxJava Observable, alih-alih Flow — LiveData. Room dengan Java mendukung semua anotasi yang sama, tetapi memerlukan lebih banyak kode boilerplate untuk operasi asinkron.

Bagaimana cara kerja enkripsi database Room?

Room mendukung enkripsi melalui SQLCipher dari Zetetic. Alih-alih Room.databaseBuilder, gunakan SupportFactory dari pustaka net.zetetic:android-database-sqlcipher dengan memberikan kata sandi enkripsi. Semua data pada disk akan dienkripsi secara transparan untuk query DAO.

Ringkasan

  • Room — pustaka ORM Jetpack untuk SQLite dengan pemeriksaan SQL pada tahap kompilasi.
  • @Entity mendeskripsikan tabel, @PrimaryKey — pengidentifikasi, @ColumnInfo — nama kolom.
  • @Dao berisi metode dengan @Query, @Insert, @Update dan @Delete untuk akses data.
  • RoomDatabase menyatukan Entity dan DAO, dibuat melalui Room.databaseBuilder.
  • Migrasi (Migration) mendeskripsikan skrip SQL untuk mengubah skema tanpa kehilangan data.
  • Room secara native mendukung Kotlin Coroutines (suspend) dan Flow untuk pembaruan UI reaktif.
  • Untuk daftar besar, gunakan Paging 3 dengan Room melalui PagingSource untuk pemuatan halaman.

Kami akan mengembangkan aplikasi seluler turnkey

IT Sectr membuat aplikasi iOS dan Android untuk startup dan bisnis sejak 2017. Kami akan memberi saran dan mengusulkan solusi terbaik.

Diskusikan proyek

Baca juga