Room DB๋?
Room์ ์๋๋ก์ด๋ ์ฑ์ ๋ด์ฅ DB์ ๋ฐ์ดํฐ๋ฅผ ์ ์ฅํ๊ธฐ ์ํด ์ฌ์ฉ๋๋ค.
Jetpack ๋ผ์ด๋ธ๋ฌ๋ฆฌ ์ค ํ๋๋ก DB ๋ฐ์ดํฐ๋ฅผ Java/Kotlin์ผ๋ก ๋ณํํ๋ ORM ๋ผ์ด๋ธ๋ฌ๋ฆฌ์ด๋ค.
Room์ SQLite์ ์ถ์ ๋ ์ด์ด ์์ ์ ๊ณตํ๊ณ ์์ผ๋ฉฐ, SQLite์ ๋ชจ๋ ๊ธฐ๋ฅ์ ์ ๊ณตํ์ฌ ํธํ ๋ฐ์ดํฐ๋ฒ ์ด์ค ์ ๊ทผ์ ํ์ฉํ๋ค.
LiveData๋ RxJava์ ๊ฐ์ด Observation ํํ๋ ์ง์ํ๋ฏ๋ก ์ํคํ ์ณ ํจํด์๋ ์ ์ฉ์ด ๋งค์ฐ ์ฝ๋ค.
SharedPreferences์ ์ฐจ์ด
SharedPreferences๋ ์ฑ์ ๋ก์ปฌ์ ๋ฐ์ดํฐ๋ฅผ ์ ์ฅํ ์ ์์ง๋ง, ๊ฐ๋ฒผ์ด ๋ฐ์ดํฐ๋ฅผ์ ์ฅํ ๋ชฉ์ ์ผ๋ก ๋ก์ปฌ DB๋ฅผ ์ฌ์ฉํ๋ค.
- ์๋ฅผ๋ค์ด,
์๋ฒ์ ํต์ ํ ๋ ์ธ Stringํ access_token์ ์ ์ฅํ ๋
Room DB๋ ํฐ ์ฌ์ด์ฆ์ ๋ฐ์ดํฐ๋ฅผ ์ ์ฅํ ๋ชฉ์ ์ผ๋ก ์ฌ์ฉํ๋ค.
Room ์ฌ์ฉ์ด ๊ถ์ฅ๋๋ ์ด์
- Room์ LiveData์ RxJava๋ฅผ ์ํObservation์ผ๋ก ์์ฑํ์ฌ ๋์ํ ์ ์์ง๋ง SQLite๋ ๊ทธ๋ ์ง ์๋ค.
- Room์ SQLite์ ํฌํจํ๊ณ ์๊ธฐ ๋๋ฌธ์ SQLite๋ฅผ ํ์ฉํ์ฌ ๋ฐ์ดํฐ ์ ๊ทผ์ด ํธ๋ฆฌํ๊ณ ์ ์ง๋ณด์๊ฐ ์ฉ์ดํ๋ฉฐ ๋ง์ด๊ทธ๋ ์ด์ ๋ ๊ฐ๋จํ๋ค.
- SQLite์ ๋ฌ๋ฆฌ ์ปดํ์ผ ํ์์ ์ฟผ๋ฆฌ์ ์ ํฉ์ฑ์ ํ์ธํ ์ ์๋ค. ์ฆ, SQLite๋ณด๋ค ํธ๋ฆฌํ DB๋ผ๊ณ ์๊ฐํ๋ฉด ๋๋ค.
SQLite์ ๋ํ ๋ ์์ธํ ๋ด์ฉ์ ์๋ ๋งํฌ ์ฐธ๊ณ
Room์ 3๊ฐ์ง ๊ตฌ์ฑ์์
Entity
- DB์์ Table์ ๋ํ๋ธ๋ค.
- @Entity๋ก ์ ์ธํ๋ค.
Dao (Data Access Objects)
- ๋ฐ์ดํฐ์ Access ํ ์ ์๋ Interface
- @Dao๋ก ์ ์ธํ๋ค.
Room DataBase
- abstract class๋ก ์ ์ธํ๊ณ Room Database๋ฅผ ์์ ๋ฐ๋๋ค.
- @Database๋ก ์ ์ธํ๋ค.
- DB์์ ์ฌ์ฉ๋ ํ ์ด๋ธ์ ์ ๋ณด(entitiy)๊ฐ ํ์ํ๊ณ , version ์ ๋ณด๊ฐ ํ์ํ๋ค.
@Database(entities = [TextEntity::class], version = 1)
- App์ด ์ ๋ฐ์ดํธ ๋์ด์ DB๊ฐ ๋ณ๊ฒฝ๋ ๊ฒฝ์ฐ ์ด์ DB์๊ตฌ๋ถ์ด ํ์ํ๋ฏ๋ก version ์ int ๊ฐ์ ๋ฃ์ด์ ๊ด๋ฆฌํ๋ค.
์ฌ์ฉ ์์
Build.gradle
id 'kotlin-kapt'
// ROOM
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")
// Coroutine
implementation("org.jetbrains.kotlinx:kotlinx-coroutines-android:1.6.0")
TextEntity.kt
- Entity๋ ์ค์ฒด(๊ฐ์ฒด)์ด๋ค. ํํ ๋ฐ์ดํฐ๋ฒ ์ด์ค์์ ๊ฐ๋ ์คํค๋ง๋ฅผ ๋ปํ๋ฉฐ ์ฝ๊ฒ ํ ์ด๋ธ์ด๋ผ๊ณ ์๊ฐํ๋ฉด ๋๋ค.
- data class๋ฅผ ์ ์ํ๊ณ @Entity ์ด๋ ธํ ์ด์ ์ ํ์ํ๋ค.
- Entity์๋ ํ๋ ์ด์์ ๊ธฐ๋ณธํค๋ฅผ ์ค์ ํด์ผ ํ๋ฉฐ, @PrimaryKey๋ก ์ ์ธ๋ ๋ณ์๊ฐ ๊ธฐ๋ณธํค๋ค.
- ๊ธฐ๋ณธํค๋ ๋ณตํฉํค๋ก ์ด๋ฃจ์ด์ง ์ ์์ผ๋ฉฐ ์๋์ ๊ฐ์ด ์ด๋ ธํ ์ด์ ์์ ์ค์ ํด์ฃผ๋ฉด ๋๋ค.
@Entity(primaryKeys = arrayOf("firstName", "lastName"))
import androidx.room.ColumnInfo
import androidx.room.Entity
import androidx.room.PrimaryKey
// ํ
์ด๋ธ ์ด๋ฆ ์ค์
@Entity(tableName = "text_table")
data class TextEntity(
@PrimaryKey(autoGenerate = true)
// @CcolumnInfo
// ๊ธฐ๋ณธ์ ์ผ๋ก ๋ณ์ ์ด๋ฆ์ด ์ด ์ด๋ฆ์ด ๋๋ค. ๋ง์ฝ ๋ณ๋๋ก ์ด ์ด๋ฆ์ ์ค์ ํ๊ณ ์ถ๋ค๋ฉด name ์์ฑ์ ์ฃผ๋ฉด ๋๋ค
@ColumnInfo(name = "id")
var id: Int,
@ColumnInfo(name = "text")
var text: String
)
TextDao.kt
- DAO ๋ฅผ ํตํด ์ฟผ๋ฆฌ๋ฌธ์ ์ฌ์ฉํ์ฌ ๋ฐ์ดํฐ๋ฒ ์ด์ค์ ๋ฐ์ดํฐ์ ์ ๊ทผํ ์ ์๋ค.
- DAO ๋ก ์ ์ํ๊ธฐ ์ํด์ @Dao๋ผ๋ ์ด๋ ธํ ์ด์ ์ด ํ์ํ๋ฉฐ, ์ธํฐํ์ด์ค๋ก ์์ฑ๋๋ค.
- @Query ๋ฅผ ํตํด ์ง์ SQL์ ์์ฑํ ์ ์๋ค. ๊ทธ ์ธ์๋ @Insert @Delete @Update ๋ฑ์ผ๋ก ๊ฐํธํ๊ฒ ๊ตฌํํ ์ ์๋ ๊ธฐ๋ฅ์ ์ ๊ณตํ๋ค.
- ํ์ฉ ๋ฐฉ๋ฒ์ด ๋ง์ผ๋ ์์ธํ๊ฑด ์๋๋ก์ด๋ ๊ฐ๋ฐ์ ๋ฌธ์๋ฅผ ์ฐพ์๋ณด๋ ๊ฒ์ ์ถ์ฒํ๋ค.
import androidx.room.Dao
import androidx.room.Insert
import androidx.room.OnConflictStrategy
import androidx.room.Query
@Dao
interface TextDao {
@Query("SELECT * FROM text_table")
fun getAllData(): List<TextEntity>
@Insert(onConflict = OnConflictStrategy.IGNORE)
fun insert(text: TextEntity)
@Query("DELETE FROM text_table")
fun deleteAllData()
}
TextDatabase.kt
Room ์์ ๋ฐ์ดํฐ๋ฒ ์ด์ค๋ฅผ ์ ์ํ๊ธฐ ์ํด์๋ @Database ๋ฅผ ์ฌ์ฉํ๋ฉฐ ํด๋์ค๋ ์ถ์ ํด๋์ค๋ก ์์ฑ๋์ด์ผ ํ๋ค.
์ถ์ ํด๋์ค๋ RoomDatabse() ๋ฅผ ์์ํด์ผ ํ๋ฉฐ ๋งค๊ฐ ๋ณ์๊ฐ ์๋ ์ถ์ ๋ฉ์๋๋ฅผ ํฌํจํด์ผ ํ๋ค.
์ด๋ ธํ ์ด์ ์๋ ๋ฐ์ดํฐ๋ฒ ์ด์ค์ ์ฐ๊ฒฐ๋ ํญ๋ชฉ์ ๋ชฉ๋ก๊ณผ ๋ฒ์ ์ ํฌํจํด์ผ ํ๋ค.
import android.content.Context
import androidx.room.Database
import androidx.room.Room
import androidx.room.RoomDatabase
@Database(entities = [TextEntity::class], version = 1)
abstract class TextDatabase : RoomDatabase() {
abstract fun textDao() : TextDao
companion object{
@Volatile
private var INSTANCE : TextDatabase? = null
fun getDatabase(
context : Context
) : TextDatabase{
return INSTANCE ?: synchronized(this){
val instance = Room.databaseBuilder(
context.applicationContext,
TextDatabase::class.java,
"text_database"
)
.fallbackToDestructiveMigration()
.build()
INSTANCE = instance
instance
}
}
}
}
MainActivity.kt
์ฌ๊ธฐ์ ์ฝ๋ฃจํด์ ์ฌ์ฉํ๋ ์ด์ ๋ ๋ณด๋ค์ํผ ๋์์ ํ ๋๋ง๋ค ๋ก๊ทธ๋ฅผ ํตํด ๋ฐ์ดํฐ๋ฅผ ๊ฐ์ ธ์ค๊ณ ์๋ค.
์ด ๋ ์ฝ๋ฃจํด์ ์ฌ์ฉํ์ง ์์ผ๋ฉด ์๋์ ๊ฐ์ ์ค๋ฅ๋ฅผ ๋ง๋๊ฒ ๋๋ค.
java.lang.IllegalStateException: Cannot access database on the main thread since it may potentially lock the UI for a long period of time.
์์ธ์ ์๋๋ก์ด๋๋ฐ์ดํฐ๋ฒ ์ด์ค ์ฟผ๋ฆฌ๊ฐ ๋ฉ์ธ ์ค๋ ๋๋ฅผ ์ ์ ํ ๊ฒ์ ์ผ๋ คํ์ฌ ๋ฉ์ธ ์ค๋ ๋๊ฐ ์๋ ๋ค๋ฅธ ์ค๋ ๋์์ ์ฟผ๋ฆฌ๋ฅผ ์คํํ ๊ฒ์ ๊ฐ์ํ๋ ๊ฒ์ด๋ค.
๋ฐ๋ผ์ ์ฟผ๋ฆฌ๋ฅผ CoroutineScope ๋ด๋ถ์์ ์คํํ๋ฉด ์ฝ๋ฃจํด์ IO ์ค๋ ๋๋ฅผ ์ฌ์ฉํ๊ธฐ ๋๋ฌธ์ ์๋ฌ๋ฅผ ํผํ ์ ์๋ค.
import androidx.appcompat.app.AppCompatActivity
import android.os.Bundle
import android.util.Log
import android.widget.Button
import android.widget.EditText
import kotlinx.coroutines.CoroutineScope
import kotlinx.coroutines.Dispatchers
import kotlinx.coroutines.launch
class MainActivity : AppCompatActivity() {
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_main)
val db = TextDatabase.getDatabase(this)
val inputArea = findViewById<EditText>(R.id.textInputArea)
val insertBtn = findViewById<Button>(R.id.insert)
val getAllBtn = findViewById<Button>(R.id.getData)
val deleteBtn = findViewById<Button>(R.id.delete)
// ๋ฐ์ดํฐ ์ฝ์
insertBtn.setOnClickListener {
CoroutineScope(Dispatchers.IO).launch {
db.textDao().insert(TextEntity(0, inputArea.text.toString()))
Log.d("MainActivity", db.textDao().getAllData().toString())
inputArea.setText("")
}
}
// ๋ฐ์ดํฐ ๋ชจ๋ ๊ฐ์ ธ์ค๊ธฐ
getAllBtn.setOnClickListener {
CoroutineScope(Dispatchers.IO).launch {
Log.d("MainActivity", db.textDao().getAllData().toString())
}
}
// ๋ฐ์ดํฐ ๋ชจ๋ ์ญ์
deleteBtn.setOnClickListener {
CoroutineScope(Dispatchers.IO).launch {
db.textDao().deleteAllData()
Log.d("MainActivity", db.textDao().getAllData().toString())
}
}
}
}
์คํ ๊ฒฐ๊ณผ
1. EditText์ hihi ์ ๋ ฅํ๊ณ ์ฝ์ ํ๋ค.
2. hihi ๋ฅผ ํ ๋ฒ ๋ ์ฝ์ ํ๋ค.
3. hello ๋ฅผ ์ฝ์ ํ๋ค.
4. ๋ฐ์ดํฐ๋ฅผ ๋ถ๋ฌ์ค๊ธฐ ๋ฒํผ์ ๋๋ฅด๋ฉด ๋ค์๊ณผ ๊ฐ์ด ์ถ๋ ฅ๋๋ค.
[TextEntity(id=1, text=hihi), TextEntity(id=2, text=hihi), TextEntity(id=3, text=hello)]
5. ๋ฐ์ดํฐ ์ญ์ ๋ฅผ ๋๋ฅด๋ฉด ๋ค์๊ณผ ๊ฐ์ด ์ถ๋ ฅ๋์ด ๊ฒฐ๊ณผ๋ฅผ ์ ์ ์๋ค.
[ ]
์ฐธ๊ณ
'๐ Development > Android' ์นดํ ๊ณ ๋ฆฌ์ ๋ค๋ฅธ ๊ธ
[Java ์๋ฐ, Android ์๋๋ก์ด๋] ์ฑํ ๋ฐฉ ๋ง๋ค๊ธฐ (0) | 2023.07.17 |
---|---|
[์๋๋ก์ด๋] Jetpack์ ViewModel์ด๋? (์ฌ์ฉ๋ฒ ์์ ) (0) | 2023.05.22 |
[์๋๋ก์ด๋] JetPack์ LiveData๋? (0) | 2023.05.22 |
[์๋๋ก์ด๋] Local DB SQLite ์ด๋? (์ฌ์ฉ๋ฒ ์์ ) (0) | 2023.05.17 |
[์๋๋ก์ด๋] Retrofit2 ๋? (์ฌ์ฉ๋ฒ ์์ ) (1) | 2023.05.16 |