Effectuer une migration de SQLite vers Room

La bibliothèque de persistance Room offre de nombreux avantages en comparaison avec l'utilisation directe des API SQLite :

  • Une vérification des requêtes SQL au moment de la compilation.
  • Des annotations pratiques qui réduisent le code récurrent qui peut s'avérer répétitif et être sujet aux erreurs.
  • Des chemins de migration simplifiés pour les bases de données.

Si votre application utilise actuellement une implémentation sans Room de SQLite, lisez cette page pour découvrir comment migrer votre application afin d'utiliser Room. Si Room est la première implémentation de SQLite que vous utilisez dans votre application, consultez la section Enregistrer des données dans une base de données locale à l'aide de Room pour obtenir des informations de base sur l'utilisation.

Procédure de migration

Pour migrer votre implémentation de SQLite vers Room, procédez comme suit : Si votre implémentation de SQLite utilise une base de données volumineuse ou des requêtes complexes, vous pouvez choisir une migration progressive vers Room. Consultez la section Migration par incréments pour en savoir plus sur la stratégie de migration par incréments.

Mettre à jour les dépendances

Pour utiliser Room dans votre application, vous devez inclure les dépendances appropriées dans le fichier build.gradle de votre application. Pour obtenir les dépendances Room les plus récentes, consultez la section Configuration.

Convertir les classes de modèle en entités de données

Room utilise des entités de données pour représenter les tables de la base de données. Chaque classe d'entité représente une table et comporte des champs qui représentent les colonnes de cette table. Procédez comme suit pour convertir vos classes de modèle existantes en entités Room :

  1. Annotez la déclaration de classe avec @Entity pour indiquer qu'il s'agit d'une entité Room. Vous pouvez éventuellement utiliser la propriété tableName pour indiquer que le nom de la table obtenue doit être différent du nom de la classe.
  2. Annotez le champ de clé primaire avec @PrimaryKey.
  3. Si l'une des colonnes de la table obtenue doit porter un nom différent de celui du champ correspondant, annotez le champ avec @ColumnInfo et définissez la propriété name sur le nom de colonne approprié.
  4. Si la classe comporte des champs que vous ne souhaitez pas conserver dans la base de données, annotez-les avec @Ignore afin d'indiquer que Room ne doit pas créer de colonnes pour ces champs dans la table correspondante.
  5. Si la classe comporte plusieurs méthodes de constructeur, indiquez quel constructeur Room doit utiliser en annotant tous les autres constructeurs avec @Ignore.

Kotlin

@Entity(tableName = "users")
data class User(
  @PrimaryKey
  @ColumnInfo(name = "userid") val mId: String,
  @ColumnInfo(name = "username") val mUserName: String?,
  @ColumnInfo(name = "last_update") val mDate: Date?,
)

Java

@Entity(tableName = "users")
public class User {

  @PrimaryKey
  @ColumnInfo(name = "userid")
  private String mId;

  @ColumnInfo(name = "username")
  private String mUserName;

  @ColumnInfo(name = "last_update")
  private Date mDate;

  @Ignore
  public User(String userName) {
    mId = UUID.randomUUID().toString();
    mUserName = userName;
    mDate = new Date(System.currentTimeMillis());
  }

  public User(String id, String userName, Date date) {
    this.mId = id;
    this.mUserName = userName;
    this.mDate = date;
  }

}

Créer des DAO

Room utilise des objets d'accès aux données (DAO) pour définir les méthodes qui accèdent à la base de données. Suivez les conseils de la section Accéder aux données à l'aide des DAO de Room pour remplacer vos méthodes de requête existantes par des DAO.

Créer une classe de base de données

Les implémentations de Room utilisent une classe de base de données pour gérer une instance de la base de données. Votre classe de base de données doit étendre RoomDatabase et référencer l'ensemble des entités et des DAO que vous avez définis.

Kotlin

@Database(entities = [User::class], version = 2)
@TypeConverters(DateConverter::class)
abstract class UsersDatabase : RoomDatabase() {
    abstract fun userDao(): UserDao
}

Java

@Database(entities = {User.class}, version = 2)
@TypeConverters(DateConverter.class)
public abstract class UsersDatabase extends RoomDatabase {
  public abstract UserDao userDao();
}

Définir un chemin de migration

Étant donné que le numéro de version de la base de données évolue, vous devez définir un objet Migration pour indiquer un chemin de migration afin que Room conserve les données existantes dans la base de données. Tant que le schéma de la base de données ne change pas, l'implémentation peut être vide.

Kotlin

val MIGRATION_1_2 = object : Migration(1, 2) {
  override fun migrate(database: SupportSQLiteDatabase) {
    // Empty implementation, because the schema isn't changing.
  }
}

Java

static final Migration MIGRATION_1_2 = new Migration(1, 2) {
  @Override
  public void migrate(SupportSQLiteDatabase database) {
    // Empty implementation, because the schema isn't changing.
  }
};

Pour en savoir plus sur les chemins de migration de bases de données dans Room, consultez la section Effectuer une migration de votre base de données.

Mettre à jour l'instanciation de la base de données

Après avoir défini une classe de base de données et un chemin de migration, vous pouvez utiliser Room.databaseBuilder pour créer une instance de votre base de données avec le chemin de migration appliqué :

Kotlin

val db = Room.databaseBuilder(
          applicationContext,
          AppDatabase::class.java, "database-name"
        )
          .addMigrations(MIGRATION_1_2).build()

Java

db = Room.databaseBuilder(
          context.getApplicationContext(),
          UsersDatabase.class, "database-name"
        )
          .addMigrations(MIGRATION_1_2).build();

Tester l'implémentation

Veillez à tester votre nouvelle implémentation de Room :

Migration par incréments

Si votre application utilise une base de données volumineuse et complexe, vous ne pourrez peut-être pas migrer votre application vers Room en une seule fois. À la place, vous pouvez éventuellement implémenter les entités de données et la base de données Room dans un premier temps, puis migrer vos méthodes de requête vers des DAO ultérieurement. Pour ce faire, remplacez votre classe d'assistance de base de données personnalisée par l'objet SupportSQLiteOpenHelper que vous recevez de RoomDatabase.getOpenHelper().

Ressources supplémentaires

Pour en savoir plus sur la migration de SQLite vers Room, consultez les ressources supplémentaires suivantes :

Blogs