Skip to content

Latest commit

 

History

History
182 lines (135 loc) · 8.11 KB

part-1.md

File metadata and controls

182 lines (135 loc) · 8.11 KB

Room - Part 1 - Introduction

Developer document

Get the dependencies

https://developer.android.com/training/data-storage/room#setup

def roomVersion = "2.4.0"

implementation("androidx.room:room-runtime:$roomVersion")
annotationProcessor("androidx.room:room-compiler:$roomVersion")

// To use Kotlin annotation processing tool (kapt)
kapt("androidx.room:room-compiler:$roomVersion")

// optional - Kotlin Extensions and Coroutines support for Room
implementation("androidx.room:room-ktx:$roomVersion")

Also needs kotlin-kapt plugin.

plugins {
    ...
    id "kotlin-kapt"
}

Full sample code

// Entity
// ===================================================================================

                                                    // Entity defines table inside the database.
                                                    // An entity data class can be used to refer
                                                    // to individual entries (row) in the table.
                                                    
                                                    // This is similar to model class.

@Entity(tableName = "Table1")
data class Table1Entity (
    @PrimaryKey(autoGenerate = true)
    val id: Int,
    val name: String
)

// ===================================================================================



// DAO
// ===================================================================================

                                                    // DAO - Data Access Objects
                                                    // This is not an object though.
                                                    // DAO is an interface,
                                                    // having methods for operations on table.
                                                    
                                                    // IMPORTANT!
                                                    // 1. Needs to be anotated with @Dao
                                                    // 2. Appropriate annotation.
                                                    // 3. @Insert, @Delete, @Update
                                                    //    methods cannot have any other argument 
                                                    //    other than type of the table entity.
                                                    // 4. @Query - needs to have an 
                                                    //    SQL query statement.

@Dao
interface Table1Dao {

    @Insert(onConflict = OnConflictStrategy.ABORT)   // onConflit optional. Default - ABORT
    suspend fun insertRecord(record: Table1Entity)

    @Delete
    suspend fun deleteRecord(record: Table1Entity)

    @Update
    suspend fun updateRecord(record: Table1Entity)

    @Query("SELECT * FROM Table1")
    suspend fun getAllRecords(): List
                                                    // Note the table name in SQL query matches
                                                    // with @Entity annotation "tableName",
                                                    // present in the "Table1Entity" data class.
                                                    
    
    @Query("SELECT EXISTS(SELECT * FROM Table1 WHERE name is :name)")
    suspend fun isPresent(name: String): Boolean
                                                    // This method checks if the name entry exists.
                                                    // Check how the method is passed to the query
                                                    // (using a colon :)
                                                    // We cannot use in argument like ${record.name}
                                                    // as dot operator is not supported.
                                                    // @Query can take only primary type variables.
}

// ===================================================================================



//  Database class
// ===================================================================================

                                                    // This "connects" the entity data class
                                                    // and the DAO interface.
                                                    
                                                    // IMPORTANT!
                                                    // 1. To be annotated with @Database,
                                                    //    which takes input of array of entities,
                                                    //    (thus it knows the table schemas).
                                                    //    "version" is also mandatory.
                                                    // 2. Must be abstract class, 
                                                    //    extending "RoomDatabase" class.
                                                    // 3. Must have abstract functions with 
                                                    //    return type as DAO interface.

@Database(entities = [Table1Entity::class], version = 1)
abstract class AppDb: RoomDatabase() {
    abstract fun table1Dao(): Table1Dao
}

// ===================================================================================



// Create instance of Database class
// For singleton, create in a kotlin file, not inside class.
// ===================================================================================

                                                    // Needs context for Room.databaseBuilder
                                                    // Argument 1 - context
                                                    // Argument 2 - previuosly defined 
                                                    //    database class extending RoomDatabase()
                                                    // Argument 3 - name of database file
                                                    
                                                    // Creating database instance 
                                                    // is an expensive operation.
                                                    // Hence we create once and 
                                                    // store that in a variable.

private var DbSingleton : AppDb? = null
fun getAppDb(context: Context): AppDb {
    return DbSingleton ?:
    Room.databaseBuilder(context, AppDb::class.java, "Name.db").build().apply {
        DbSingleton = this
    }
}

// ===================================================================================



// Call the DAO interface functions
// Call inside a coroutine scope.
// ===================================================================================

                                                    // Call the previously defined getAppDb()
                                                    // function.
                                                    // This is an instance of "AppDb" class
                                                    // which contained "table1Dao()" function.
                                                    // Use that method to get the instance of
                                                    // DAO interface and then use the methods
                                                    // defined in "Table1Dao" interface.

class MainActivity: AppCompatActivity() {

    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)

        CoroutineScope(IO).launch {
            getAppDb(this@MainActivity).table1Dao().run {
                insertRecord(
                    Table1Entity(0, "sample_name_776")
                )
                println("DB result: ${getAllRecords()}, size: ${getAllRecords().size}")
            }
        }
    }
    
}

// ===================================================================================