Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to add new tables in library with Room?

I am planning to start the migration of an existing app to Architecture Components and one of my doubts is how should I organize the new code.

I have some tables that are added in a personal library that's only included in some flavors, how can those Entities and DAOs be added to the main application if the database class exists on the main application?

Should I add another database class to the library? If so, wouldn't it collide with existing Database class in the main application?

I have been searching, but haven't been able to find any example or tutorial...

Edit to clarify Database question

From the docs I understand that in the Database abstract class, you have to tell wich Entities exists and also create access methods for the DAOs. How could this be done if there are entities in the library?

@Database(entities = {User.class}, version = 1)
public abstract class AppDatabase extends RoomDatabase {
    public abstract UserDao userDao();
}
like image 693
Eylen Avatar asked Feb 12 '18 09:02

Eylen


2 Answers

@Database(version = 1, entities = {User.class, Book.class})
abstract class AppDatabase extends RoomDatabase {
     // BookDao is a class annotated with @Dao.
     abstract public BookDao bookDao();
     // UserDao is a class annotated with @Dao.
     abstract public UserDao userDao();
     // UserBookDao is a class annotated with @Dao.
     abstract public UserBookDao userBookDao();
}

If you want to update the Room database and add table...just add another entity then update the version if you add another entity like Movies table.. do something like this

@Database(version = 2, entities = {User.class, Book.class, Movies.class})
abstract class AppDatabase extends RoomDatabase {
     // BookDao is a class annotated with @Dao.
     abstract public BookDao bookDao();
     // UserDao is a class annotated with @Dao.
     abstract public UserDao userDao();
     // UserBookDao is a class annotated with @Dao.
     abstract public UserBookDao userBookDao();
     // MoviesDao is a class annotated with @Dao.
     abstract public MoviesDao moviesDao();
     // UserMoviesDao is a class annotated with @Dao.
     abstract public UserMoviesDao userMoviesDao();
}

for reference you can check ... this

like image 81
Santanu Sur Avatar answered Oct 23 '22 16:10

Santanu Sur


The Room persistence library supports incremental migrations with the Migration classes to address this need. Each Migration subclass defines a migration path between a startVersion and an endVersion.

So, the right answer (and the correct way because you should not use fallbackToDestructiveMigration) is :

Add your new table as a java class

@Entity(tableName = "Fruit")
public class Fruit implements Parcelable {
        
        @PrimaryKey(autoGenerate = true)
        @ColumnInfo(index = true, name = "id")
        private int id;
    
        @ColumnInfo(name = "name")
        private String name;
    
    ...
    
    }

Update your database version AND add your entity in entities declaration (you add the class definition to tells room should take the class into consideration) and add your dao getter

@Database(version = 2, entities = {User.class, Fruit.class})
abstract class AppDatabase extends RoomDatabase {
     
     abstract public UserDao userDao();
     
     abstract public FruitDao fruitDao();
}

Add migration sql script with your database builder like this

 public 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`))");
        }
    };
    
    Room.databaseBuilder(getApplicationContext(), MyDb.class, "database-name")
            .addMigrations(MIGRATION_1_2).build();

Source : https://developer.android.com/training/data-storage/room/migrating-db-versions

like image 40
Zhar Avatar answered Oct 23 '22 16:10

Zhar