Scrivi query DAO asincrone

Per evitare che le query blocchino la UI, la stanza virtuale non consente l'accesso al database su nel thread principale. Questa limitazione significa che devi rendere asincrone le query DAO. La libreria Room include integrazioni con diversi framework per fornire l'esecuzione di query asincrone.

Le query DAO rientrano in tre categorie:

  • Query di scrittura one-shot che inseriscono, aggiornano o eliminano dati nel database.
  • Query di lettura one-shot che leggono i dati dal database una sola volta e restituiscono un risultato con lo snapshot del database in quel momento.
  • Query di lettura osservabile che leggono i dati dal database ogni volta le tabelle di database sottostanti cambiano ed emettono nuovi valori per riflettere quelli modifiche.

Opzioni di linguaggio e framework

La stanza virtuale fornisce il supporto per l'integrazione per l'interoperabilità con un linguaggio specifico funzionalità e librerie. La tabella seguente mostra i tipi di reso applicabili in base sul tipo di query e sul framework:

Tipo di query Funzionalità del linguaggio Kotlin RxJava Guava Jetpack Lifecycle
Scrittura one-shot Coroutine (suspend) Single<T>, Maybe<T>, Completable ListenableFuture<T> N/D
Lettura one-shot Coroutine (suspend) Single<T>, Maybe<T> ListenableFuture<T> N/D
Lettura osservabile Flow<T> Flowable<T>, Publisher<T>, Observable<T> N/D LiveData<T>

Questa guida illustra tre possibili modi per utilizzare queste integrazioni per implementare query asincrone nei DAO.

Kotlin con Flow e couroutine

Kotlin offre funzionalità linguistiche che ti consentono di scrivere query asincrone senza framework di terze parti:

  • Nella stanza 2.2 e successive, puoi usare Flusso per scrivere query osservabili.
  • Nella stanza 2.1 e successive, puoi utilizzare la parola chiave suspend per rendere il tuo DAO le query in modo asincrono utilizzando le coroutine di Kotlin.
di Gemini Advanced.

Java con RxJava

Se la tua app utilizza il linguaggio di programmazione Java, puoi utilizzare caratteri di ritorno specializzati del framework RxJava per scrivere metodi DAO asincroni. Le camere offrono supporto per i seguenti tipi restituiti RxJava 2:

Inoltre, Room 2.3 e versioni successive supportano RxJava 3.

Java con LiveData e Guava

Se la tua app utilizza il linguaggio di programmazione Java e non desideri utilizzare RxJava, puoi utilizzare le seguenti alternative per scrivere query:

  • Puoi utilizzare la classe wrapper LiveData di Jetpack per scrivere query osservabili asincrone.
  • Puoi utilizzare lo ListenableFuture<T> un wrapper per la scrittura di query one-shot asincrone.

Scrivere query one-shot asincrone

Le query one-shot sono operazioni di database che vengono eseguite una sola volta e acquisiscono uno snapshot di dati al momento dell'esecuzione. Di seguito sono riportati alcuni esempi di modelli query one-shot:

Kotlin

@Dao
interface UserDao {
    @Insert(onConflict = OnConflictStrategy.REPLACE)
    suspend fun insertUsers(vararg users: User)

    @Update
    suspend fun updateUsers(vararg users: User)

    @Delete
    suspend fun deleteUsers(vararg users: User)

    @Query("SELECT * FROM user WHERE id = :id")
    suspend fun loadUserById(id: Int): User

    @Query("SELECT * from user WHERE region IN (:regions)")
    suspend fun loadUsersByRegion(regions: List<String>): List<User>
}

Java

@Dao
public interface UserDao {
    @Insert(onConflict = OnConflictStrategy.REPLACE)
    public Completable insertUsers(List<User> users);

    @Update
    public Completable updateUsers(List<User> users);

    @Delete
    public Completable deleteUsers(List<User> users);

    @Query("SELECT * FROM user WHERE id = :id")
    public Single<User> loadUserById(int id);

    @Query("SELECT * from user WHERE region IN (:regions)")
    public Single<List<User>> loadUsersByRegion(List<String> regions);
}

Java

@Dao
public interface UserDao {
    // Returns the number of users inserted.
    @Insert(onConflict = OnConflictStrategy.REPLACE)
    public ListenableFuture<Integer> insertUsers(List<User> users);

    // Returns the number of users updated.
    @Update
    public ListenableFuture<Integer> updateUsers(List<User> users);

    // Returns the number of users deleted.
    @Delete
    public ListenableFuture<Integer> deleteUsers(List<User> users);

    @Query("SELECT * FROM user WHERE id = :id")
    public ListenableFuture<User> loadUserById(int id);

    @Query("SELECT * from user WHERE region IN (:regions)")
    public ListenableFuture<List<User>> loadUsersByRegion(List<String> regions);
}

Scrivere query osservabili

Le query osservabili sono operazioni di lettura che emettono nuovi valori ogni volta che modifiche a qualsiasi tabella a cui fa riferimento la query. Un modo per utilizzarlo è mantenere aggiornato un elenco visualizzato di elementi man mano che gli elementi nel database sottostante vengono inseriti, aggiornati o rimossi. Ecco alcuni esempi esempi di query osservabili:

Kotlin

@Dao
interface UserDao {
    @Query("SELECT * FROM user WHERE id = :id")
    fun loadUserById(id: Int): Flow<User>

    @Query("SELECT * from user WHERE region IN (:regions)")
    fun loadUsersByRegion(regions: List<String>): Flow<List<User>>
}

Java

@Dao
public interface UserDao {
    @Query("SELECT * FROM user WHERE id = :id")
    public Flowable<User> loadUserById(int id);

    @Query("SELECT * from user WHERE region IN (:regions)")
    public Flowable<List<User>> loadUsersByRegion(List<String> regions);
}

Java

@Dao
public interface UserDao {
    @Query("SELECT * FROM user WHERE id = :id")
    public LiveData<User> loadUserById(int id);

    @Query("SELECT * from user WHERE region IN (:regions)")
    public LiveData<List<User>> loadUsersByRegion(List<String> regions);
}

Risorse aggiuntive

Per ulteriori informazioni sulle query DAO asincrone, consulta anche di risorse:

Campioni

Blog