PR

android Roomデータベースの使い方

Androidアプリ

アプリで取得した情報をデータベースに保存したい

こうした悩みを解決します。

姫野秀徳

組み込みエンジニアとしてメーカー勤務10年。
第二種電工事士、基本情報技術者、Code.org認定教師。
microbitを用いた電子工作&プログラミング教室を開校。
組み込み開発の実際を発信するyoutube活動も行う。

姫野秀徳をフォローする

Roomとは

Roomとは、sqliteをより簡単に、より便利に活用できるようにしたAndroid推奨のローカルデータベース運用するためのライブラリです。

詳細は公式を参照ください。

Room を使用してローカル データベースにデータを保存する  |  Android Developers
...

全体のイメージ

①エンティティでテーブルの列を定義

②DAO(テーブルを操作するSQL文の入った関数)を作成

③先ほど作成したエンティティとDAOを含めた形でデータベースを作成

④メインアクティビティにてデータベースインスタンスを取得

⑤必要に応じてDAOのメソッドを呼び出してテーブル内を操作

大きくわけてこれら5ステップです。設計においても①→⑤の順番で実装していきます。

では、例によって、下記Android公式と見比べながらいきましょう。

Room エンティティを使用してデータを定義する  |  Android Developers
...

①エンティティでテーブルの列を定義

データベースのテーブルの列情報の定義を書くのがエンティティです。

例えばentity.ktというファイルにして、MainActivityと同じフォルダに作成して下記のように書きます。

@Entity
data class User(
    @PrimaryKey(autoGenerate = true)
    val id: Int,

    val firstName: String,

    val lastName: String
)

Userというクラスにid, firstname, lastnameの3項目(列のことでカラムともいう)が入っています。

idの前についている@PrimaryKey(autoGenerate = true)について、

@はアノテーションと呼ばれ追加情報を提供する機能です。

テーブルにおいては主キーと呼ばれる一意にデータを決定するカラムが必要で、アノテーションによってidを主キーとするアノテーションを追加しています。

autoGenerate = trueを指定することで、プライマリキーの値を自動的に生成することができます。

②DAO(テーブルを操作するSQL文の入った関数)を作成

DAOはdata access objectの略で、データベースを制御するのがDAOです。

中身はデータベースを操作するSQL文とそれを実行する関数宣言で構成されます。

例えばdao.ktというファイルにして、MainActivityと同じフォルダに作成して下記のように書きます。

@Dao
interface UserDao {
    @Insert
    fun insertAll(vararg users: User)


    @Update
    fun updateUsers(vararg users: User)

    @Delete
    fun delete(user: User)

    @Query("SELECT * FROM user")
    fun getAll(): List<User>
}

エンティティでも書きましたが、アノテーションつけてそこにクエリを記述するといった使い方をします。

③エンティティとDAOを含めた形でデータベースを作成

テーブルカラム情報が入ったエンティティ、データベース操作するSQLが入ったDAOを含めたデータベースを作成します。

例えばdatabase.ktというファイルにして、MainActivityと同じフォルダに作成して下記のように書きます。

// Annotates class to be a Room Database with a table (entity) of the Word class
@Database(entities = [User::class), version = 1, exportSchema = false)
public abstract class UserDatabase : RoomDatabase() {

   abstract fun UserDao(): UserDao

   companion object {
        // Singleton prevents multiple instances of database opening at the same time.
        @Volatile
        private var INSTANCE: UserDatabase ? = null

        fun getDatabase(context: Context): UserDatabase {
            // if the INSTANCE is not null, then return it,
            // if it is, then create the database
            return INSTANCE ?: synchronized(this) {
                val instance = Room.databaseBuilder(context.applicationContext,
                        WordRoomDatabase::class.java, "word_database"
).build()
                INSTANCE = instance
                // return instance
                instance
            }
        }
   }
}

この関数はほとんどコピペで動きます。

databaseアノテーションで紐づけるエンティティを追加、抽象関数として作成したDAOを紐づけてます。

getDatabase関数はデータベースのインスタンスがあればそれを返す、無ければword_databaseという名称のデータベースを作成してそれを返します。詳細は公式を見てもらえればと思いますが、

Android Room とビュー - Kotlin  |  Android Developers
...

ここまででRoomデータベースの設計は完了です。

MainActivity.ktフォルダと同階層にentityファイル、daoファイル、databaseファイルの3つが追加で存在していますか。

もしなければ抜け洩れてますので、再度上から読み直すとよいです。

④メインアクティビティにてデータベースインスタンスを取得

メインアクティビティでデータベースを取得します。

onCreate直下でデータベースのインスタンスを取得するサンプルです。

UserDatabaseクラスのgetDatabase関数からデータベースのインスタンスを取得し、database変数に格納しています。

データベースのインスタンスに内包しているDAOも別途変数にいれます。

これでメインアクティビティでデータベースが触れるようになりました!

    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContentView(R.layout.activity_main)

        //Room用
        val database = UserDatabase.getDatabase(this) // データベースの取得
        val userDao = database.userDao()        // DAOの取得

~~~

⑤必要に応じてDAOのメソッドを呼び出してテーブル内を操作

たとえばボタンを押したらデータ追加するとか。
(下記サンプルだと毎回 tatepro, himenoしか入らない)

        var dbbtn = findViewById<Button>(R.id.dbbtn)
        dbbtn.setOnClickListener {
            val add_user = User(0, "tatepro", "himeno")

            // Userの追加
            userDao.insertAll(add_user)
        }

まとめ

①エンティティでテーブルの列を定義

②DAO(テーブルを操作するSQL文の入った関数)を作成

③先ほど作成したエンティティとDAOを含めた形でデータベースを作成

④メインアクティビティにてデータベースインスタンスを取得

⑤必要に応じてDAOのメソッドを呼び出してテーブル内を操作

大きくわけてこれら5ステップです。設計においても①→⑤の順番で実装していきます。

コメント

タイトルとURLをコピーしました