1. 程式人生 > >Android 官方架構元件--ROOM 資料庫操作簡單介紹

Android 官方架構元件--ROOM 資料庫操作簡單介紹

本文只是簡單的介紹一下怎麼在我們的專案中使用ROOM和一個簡單的小例子。       

        ROOM是Google官方推出的一個永續性資料庫,Room永續性庫提供了SQLite的抽象層,以便在充分利用SQLite的同時允許流暢的資料庫訪問。

       ROOM的引用:

compile "android.arch.persistence.room:runtime:1.0.0"
annotationProcessor 'android.arch.persistence.room:compiler:1.0.0'

       ROOM資料庫,一共有三個部分:DAO、Entity、Database;

DAO:這個元件代表了一個類或者介面作為DAO。DAOs 是Room中的主要元件,並且負責定義訪問資料庫的方法。被註解為@Database的類必須包含一個沒有引數的抽象方法並且返回註解為@Dao的類。當在編譯時生成程式碼,Room建立一個這個類的實現。(其實裡面就是對資料庫的增刪改查操作)

Entity:這個元件代表了一個持有資料行的類。對於每個entity,一個數據庫表被建立用於持有items。你必須引用entity類通過Database類中的entities陣列。每個entity欄位被持久化到資料庫中除非你註解它通過@Ignore(這個就是某一個表的具體欄位)

Database: 你可以使用這個元件建立一個數據庫holder。註解定義了一系列entities並且類的內容提供了一系列DAOs,它也是下層的主要連線 的訪問點。
註解的類應該是一個抽象的繼承

RoomDatabase的類。在執行時,你能獲得一個例項通過呼叫Room.databaseBuilder()或者 Room.inMemoryDatabaseBuilder()(這個就是資料庫,包括建立資料庫、資料庫的更新等)

1、我們建立Entity

@Entity(tableName = "tb_student",//定義表名
        indices = @Index(value = {"name", "sex"}, unique = true))
public class StudentEntity{

    @PrimaryKey //定義主鍵
    private long id;
    @ColumnInfo(name = "name")//定義資料表中的欄位名
    private String name;
    @ColumnInfo(name = "sex")
    private int sex;
    @Ignore//指示Room需要忽略的欄位或方法
    private String ignoreText;

}

首先@Entity是標識。其中tableName:是表名,PrimaryKey 主鍵是必須建立的,也是唯一的,value:就是各個欄位的宣告,"indices"、"unique"兩個可以指定某個欄位不能重複(舉例:上述的name、sex兩個欄位儲存的時候不允許有重複,不能存了一個張三、男,然後再存一個張三、男,這樣的話會直接丟擲異常),Ignore:是忽略的意思,不會儲存到資料庫中。

還有一個重要的外來鍵(也就是和其他表關聯)比如Student表中增加一個class_id欄位與Class表的id主鍵關聯:

foreignKeys ={@ForeignKey(entity=ClassEntity.class,parentColumns = "id",childColumns = "class_id")}

2、建立DAO:

@Dao
public interface StudentDao {

    @Query("SELECT * FROM tb_student")
    public List<StudentEntity> getAll();

    @Query("SELECT * FROM tb_student WHERE id IN (:ids)")
    List<StudentEntity> getAllByIds(long[] ids);

    @Query("SELECT * FROM tb_student WHERE id = :id")
    StudentEntity getById(int id);


    @Insert
    void insert(StudentEntity... entities);

    @Delete
    void delete(StudentEntity entity);

    @Update
    void update(StudentEntity entity);

}

首先@DAO是標識。裡面主要也就是增刪改查四個方法,其中查詢可以根據不同條件進行查詢。

3、建立Database:

@Database(entities = StudentEntity.class,version = 1,exportSchema = false)
public abstract class RoomDemoDatabase extends RoomDatabase {

    private static final String DB_NAME = "UserDatabase.db";
    private static volatile RoomDemoDatabase instance;

    static synchronized RoomDemoDatabase getInstance(Context context) {
        if (instance == null) {
            instance = create(context);
        }
        return instance;
    }

    private static RoomDemoDatabase create(final Context context) {
        return Room.databaseBuilder(
            context,
            RoomDemoDatabase.class,
            DB_NAME).build();
    }

    public abstract StudentDao studentDao();

}

其中@Database是宣告,裡面的entities是對應的Entity,如果有多個的話,使用如下方式:entities={StudentEntity.clss,ClassEntity.class},version是資料庫版本,

exportSchema:儲存展示資料庫的結構資訊,如果不設定的話,需要再database類上配置exportSchema = false,要不然編譯的時候會出現警告。

defaultConfig {
        minSdkVersion 19
        targetSdkVersion 26

        javaCompileOptions {
            annotationProcessorOptions {
                arguments =["room.schemaLocation":"$projectDir/schemas".toString()]
            }
        }
}

建立資料庫時有一些設定:

Room.databaseBuilder(this, RoomDemoDatabase.class,"database_name").allowMainThreadQueries(). fallbackToDestructiveMigration().build();
allowMainThreadQueries()允許再主執行緒查詢:
fallbackToDestructiveMigration():如果兩次執行的資料庫版本號不一致的話,則將上個版本的資料庫刪除重新建立。

正常我們升級資料庫操作應如下方式:

Room.databaseBuilder(getApplicationContext(), MyDb.class, "database-name")
        .addMigrations(MIGRATION_1_2, MIGRATION_2_3).build();

static final Migration MIGRATION_1_2 = new Migration(1, 2) {
    @Override
    public void migrate(SupportSQLiteDatabase database) {
        database.execSQL("CREATE TABLE `Fruit` (`id` INTEGER, "
                + "`name` TEXT, PRIMARY KEY(`id`))");
    }
};

static final Migration MIGRATION_2_3 = new Migration(2, 3) {
    @Override
    public void migrate(SupportSQLiteDatabase database) {
        database.execSQL("ALTER TABLE Book "
                + " ADD COLUMN pub_year INTEGER");
    }
};

4、我們的Entity、DAO、Database都建立完成了,可以使用程式碼測試一下了

        StudentDao dao=RoomDemoDatabase.getInstance(this).studentDao();
        StudentEntity entity=new StudentEntity();
        entity.setName("nih33o5");
        entity.setIgnoreText("ddddddd335");
        entity.setSex(1);
        entity.setId(1);
        dao.insert(entity);
        List<StudentEntity>list=dao.getAll();

例子特別簡單,主要是瞭解一下這個元件